Page 1 of 1
Pointing to a different SVG cover based on bookmap info
Posted: Thu Dec 17, 2020 8:38 pm
by llpick
Hi there,
I've been using PDF Chemistry using 1 CSS for each bookmap, which worked fine up to a point, but now I'd like to move to a single CSS.
The only problem so far has been the cover page.
The text displayed on the cover itself is lifted from the bookmap, so no problem there.
But the background image is an SVG file, linked as follows from the CSS file:
Code: Select all
@page front-page
{
background-image: url("img/front_back/front_cover.svg");
background-repeat: no-repeat;
background-size: 100%;
margin-top: 10cm;
}
I would need the image to change according to the bookmap. Possibly based on the product name (using prodinfo/prodname):
Code: Select all
<bookmeta>
(...)
<prodinfo>
<prodname>NiceProduct</prodname>
</prodinfo>
But right now I have no clue as to how I can pass this info to the CSS from the bookmap...
Any ideas? Please let me know if this is unclear.
Thank you very much.
Louis
Re: Pointing to a different SVG cover based on bookmap info
Posted: Fri Dec 18, 2020 12:12 pm
by Dan
The solution is to use an XPath to extract some information from the document, and based on it select the SVG images.
Code: Select all
@page front-page {
background-image: url(oxy_xpath("\
if(//*[contains(@class, ' topic/prodname ')][1] = 'gardening') then 'bg-gardening.svg' else\
if(//*[contains(@class, ' topic/prodname ')][1] = 'soil') then 'bg-soil.svg'\
else 'bg-default.svg'\
"));
}
The backslash is used to continue the expression string on following lines (there should be no spaces after it). For more use cases solved using XPath see:
https://www.oxygenxml.com/doc/versions/ ... aid-title6
Many regards,
Dan
Re: Pointing to a different SVG cover based on bookmap info
Posted: Fri Dec 18, 2020 2:19 pm
by llpick
Thank you Dan, this works perfectly like this.
To go a bit further: do you see any way of passing the xpath to the svg file name?
It would remove the need to add as many "if" statements as there are covers, and to update the CSS every time a new product/cover is added.
Many thanks.
Louis
Re: Pointing to a different SVG cover based on bookmap info
Posted: Fri Dec 18, 2020 7:23 pm
by Dan
Sure, you can set the name of the image file in the metadata section, in a
data element (you can put one in the prodname element for instance, or in a topic), then use XPath to extract it and pass it to the CSS url function. In the next example the name attribute of the data element is set to 'image-file-name', but you can use anything as long as you match it correctly in the XPath expression.
For more information:
https://www.oxygenxml.com/doc/versions/ ... aid-title3
Code: Select all
<map>
<title>Growing Flowers</title>
<topicmeta>
<prodinfo>
<prodname><data name="image-file-name" value="bg-1.svg"></data>gardening</prodname>
</prodinfo>
</topicmeta>
...
Code: Select all
@page front-page {
background-image: url(oxy_xpath("//*[contains(@class, ' topic/data')][@name='image-file-name'][1]/@value"));
}
Re: Pointing to a different SVG cover based on bookmap info
Posted: Mon Dec 21, 2020 4:40 pm
by chrispitude
Hi Louis,
If you have a small number of book categories, consider setting the @outputclass attribute on your top-level map element, then include this map element in your CSS selector path.
We have books, release notes, and product installation notes. Their cover pages and their headers/footers vary a bit. We have a map @outputclass value for each one, then we vary things in the CSS accordingly.
For details, see:
post58653.html?hilit=conditional%20outputclass#p58653
Re: Pointing to a different SVG cover based on bookmap info
Posted: Wed Jan 06, 2021 11:03 am
by llpick
Dear Chris and Dan, thank you both for your detailed answers.
Lots to chew on, and definitely more flexibility than I expected.
Re: Pointing to a different SVG cover based on bookmap info
Posted: Tue May 28, 2024 9:18 am
by horisonten
Dan wrote: ↑Fri Dec 18, 2020 12:12 pm
Code: Select all
@page front-page {
background-image: url(oxy_xpath("\
if(//*[contains(@class, ' topic/prodname ')][1] = 'gardening') then 'bg-gardening.svg' else\
if(//*[contains(@class, ' topic/prodname ')][1] = 'soil') then 'bg-soil.svg'\
else 'bg-default.svg'\
"));
}
Based on this solution. Can anyone please tell me why the following is not working? It seems as if it doesn't check for the 'product' at all, and simply selects the last "else" = default picture.
*[class ~= "front-page/front-page-title"]:after {
/*more stuff*/
background-image: url(oxy_xpath("\
if(//bookmap/@product[1] = 'product1') then 'resources/cover_images/product1.svg' else\
if(//bookmap/@product[1] = 'product2') then 'resources/cover_images/product2.svg'\
else 'resources/cover_images/replace_me.svg'\
"));
}
Re: Pointing to a different SVG cover based on bookmap info
Posted: Tue May 28, 2024 12:07 pm
by julien_lacour
Hello,
The query isn't working because XPath expressions are applied on the merged.html file, not on the DITA source files and in HTML5 there's no <bookmap> element. The best practice is to match on the elements class attribute as it contains the original DITA class.
You can check
this topic from our user guide for more information about how to use XPath expressions in CSS.
Regards,
Julien
Re: Pointing to a different SVG cover based on bookmap info
Posted: Tue May 28, 2024 2:11 pm
by horisonten
julien_lacour wrote: ↑Tue May 28, 2024 12:07 pm
Hello,
The query isn't working because XPath expressions are applied on the merged.html file, not on the DITA source files and in HTML5 there's no <bookmap> element. The best practice is to match on the elements class attribute as it contains the original DITA class.
You can check
this topic from our user guide for more information about how to use XPath expressions in CSS.
Regards,
Julien
Thank you very much for pointing me in the right direction
This gave me the results I was looking for:
Code: Select all
background-image: url(oxy_xpath("\
if(//*[contains(@class, ' map/map ')]/@product[1] = 'product1') then 'resources/cover_images/product1.svg' else\
if(//*[contains(@class, ' map/map ')]/@product[1] = 'product2') then 'resources/cover_images/product2.svg'\
else 'resources/cover_images/replace_me.svg'\
"));