How to insert line breaks in a PDF generated with XSL-FO - xslt

I am generating a PDF using XSL-FO and XML. In a textbox, the user can enter data like "1", then he presses ENTER, then "2", ENTER, "3", etc. But in the XML and hence in the PDF, the output is "1234567". How can I preserve the line breaks? I already tried white-space-collapse, linefeed-treatment and white-space-treatment but that didn't help.
My XSL looks like:
<xsl:template match="AddCmt">
<fo:block keep-together="always"> Additional Comments
<fo:block-container border-style="solid" height="20mm" width="170mm" space-after="5mm">
<fo:block>
<xsl:attribute name="id">
<xsl:value-of select="../CMT_ID"/>
</xsl:attribute>
<xsl:value-of select="../ANS_CMT"/>
</fo:block>
</fo:block-container>
</fo:block>
</xsl:template>
When I enter the following:
hello
medhavi
saraswat
This is the XML I get:
<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type='text/xsl' href='e:\tmm-09.3\src\pmod\WorkOrder.xsl'?>
<Root>
<WorkOrders>
<Detail>Id="ANS_436‌​_FLD_1" Label="qq">qq</Detail>
<Ans Checked="0" Id="ANS_436_FLD_2" Label="ww">ww</Ans>
<ID>ANS_436_FLD</ID>
<ANS_FLD>0|0</ANS_FLD>
<CMT_ID>ANS_436_CMT‌​</CMT_ID>
<ANS_CMT>hello medhavi saraswat</ANS_CMT>
<Warning>
<Line>warning 11</Line>
<Line>22</Line>
<Line>33</Line>
<Line>44</Line>
<Line></Line>
<Line>66</Lin‌​e>
<Line>77</Line>
<Line></Line>
</Warning>

It should work with the following xml (you should add all the attributes):
<xsl:template match="AddCmt">
<fo:block keep-together="always"> Additional Comments
<fo:block-container border-style="solid" height="20mm" width="170mm" space-after="5mm">
<fo:block wrap-option="wrap" linefeed-treatment="preserve" white-space-collapse="false" white-space-treatment="preserve">
<xsl:attribute name="id">
<xsl:value-of select="../CMT_ID"/>
</xsl:attribute>
<xsl:value-of select="../ANS_CMT"/>
</fo:block>
</fo:block-container>
</fo:block>
</xsl:template>
But as I mentioned in the comments, if your XML already has no linebreaks, there's no way your PDF will. You mentioned in your question there are no linebreaks in your XML, hence no linebreaks in the PDF.
Try checking out why there are no linebreaks in the XML. If you can provide any more information (a piece of your XML, the code you use to construct the XML, ...), please edit your answer and add the information.

Related

How to write text diagonally on a image using XSL FO

I have a text written on a certificate document which is an image, but I am trying to write the text diagonally on the image. I am unable to change it even after changing the reference orientation of the container within which the text is present.
<xsl:template match="graphicBack">
<fo:block absolute-position="absolute">
<fo:block-container position="absolute">
<fo:external-graphic xmlns:fo="http://www.w3.org/1999/XSL/Format" scaling="uniform" content-width="210mm" content-height="296.99mm">
<xsl:attribute name="src" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:value-of select="var" />
</xsl:attribute>
</fo:external-graphic>
</fo:block-container>
<fo:block-container absolute-position="absolute" left="20mm" top="200mm">
<fo:block color="#CC6133" font-family="Courier" font-style="normal" display-align="center" font-size="300px">
COPY
</fo:block>
</fo:block-container>
</fo:block>
</xsl:template>
If you are using AH Formatter, then you can use axf:transform and axf:transform-origin (see https://www.antennahouse.com/product/ahf66/ahf-ext.html#transformation) to rotate the block to an arbitrary angle.
See the 'Block transformation' example in the "Comprehensive XSL-FO Tutorials and Samples Collection" at https://www.antennahouse.com/comprehensive-xsl-fo-tutorials-and-samples-collection/.

Index mapping in XSLT-2.0

I have created index page using XSLT code. The contents name are shown to index page correctly but i want to map contents according to page number for specific title.
I am getting title with their description So I have named that block as id="TOC" and given as ref-id=”TOC” but the page number is not reflecting in my title.
Title:- Title names present in Index page.
Summary:- Title content associated with page.
The below is my XSLT-2.0 sample code:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="content_name">
<fo:block space-after="7pt" space-after.conditionality="retain" line-height="1.147" font-family="Calibri" font-size="15pt" font-weight="bold" language="FR">
<fo:inline>
<fo:leader leader-length="0pt" />
<xsl:value-of select="title"/>
<fo:page-number-citation ref-id="TOC"/>
</fo:inline>
</fo:block>
</xsl:template>
<xsl:template match="pro_list">
<fo:block space-after="15pt" space-after.conditionality="retain" line-height="1.147" font-family="Calibri" font-size="15pt" font-weight="bold" text-decoration="underline" language="FR">
<fo:inline>
<fo:leader leader-length="0pt" />
<xsl:value-of select="title" id="TOC"/>
</fo:inline>
</fo:block>
<fo:block space-after="8pt" space-after.conditionality="retain" line-height="1.147" font-family="Calibri" font-size="15pt" language="FR">
<fo:inline>
<fo:leader leader-length="0pt"/>
<xsl:value-of select="summary" disable-output-escaping="yes" />
</fo:inline>
</fo:block>
</xsl:template>
</xsl:stylesheet>
This is the output:
Contents
Title1 page no.
Title2 page no.
Title3 page no.
Suppose title1 content is associated with page2 & similar for title2-3 & title3-4, then output looks like as follows
Contents
Title1 2
Tilte2 3
Title3 4
Is there any syntax or predefined function available to do index mapping?

fo:block next to fo:table in xsl

how can I put a fo:block with a text like:
<fo:block text-align="right" font-size="48pt">
HALLO
</fo:block>
side by side / next to a my fo:table in the xsl file.
My XSL File looks so:
<?xml version="1.0" encoding="iso-8859-1"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:fo="http://www.w3.org/1999/XSL/Format"
xmlns:java="http://xml.apache.org/xslt/java" xmlns:date="java.util.Date" xmlns:sf="java.text.SimpleDateFormat"
exclude-result-prefixes="java" version="1.0">
....
....
...
<xsl:template match="Order">
<fo:table border="0.5pt solid">
<fo:table-column column-width="5cm"/>
<fo:table-body>
<fo:table-row>
<fo:table-cell>
<fo:block font-size="10pt">
delivery:
</fo:block>
</fo:table-cell>
<fo:table-cell>
<fo:block font-weight="bold" font-size="12pt">
<xsl:value-of select="#DeliveryTime"/>
</fo:block>
</fo:table-cell>
</fo:table-row>
</fo:table-body>
</fo:table>
</xsl:stylesheet>
Next to the table above in my xsl sheet I want to put the HALLO text.
If you really want this, you can specify a block-container that contains two block-containers with absolute positions placed side by side. The table goes in one, the text goes in the other.
But it's probably simpler to extend the table across the full page width and place the 'Hallo' text inside a cell, and span/merge cells if you need more room.

XSL-FO: how to do not begin a chapter in last line

I have a xml document with chapters, and sub-chapters.
I have created an XSL-FO to convert the document to PDF with apache-fop. In the PDF, chapters begin always in a new page using "break-before".
I would like sub-chapters to only start on a page if there is at least 5-10 lines free: sub-chapters do not need to begin on a new page, but it is ugly to have a title in the last line and the first paragraph in the next page.
Any idea how to perform that?
Very simple example of XML file:
<document>
<chapter title="Intro">
<sub-chapter title="any-sub-title">
Any text here
</sub-chapter>
</chapter>
</document>
XSL-FO section:
...
<xsl:for-each select="chapter">
<fo:block font-weight="bold" break-before="odd-page">
<xsl:value-of select="#title"/>
</fo:block>
<xsl:apply-templates/>
</xsl:for-each>
...
<xsl:template match="sub-chapter">
<fo:block font-weight="bold">
<xsl:value-of select="#title"/>
</fo:block>
<xsl:apply-templates/>
</xsl:template>
What I think you are looking for is widow and orphan protection. With widows and orphans, you specify the number of lines in a block that cannot be left alone on one page.
<fo:block widows="4" orphans="4">
your content here.
</fo:block>
You might get a similar behavior with the keep-together or keep-with-next attributes. See the link for a quick how-to.

Xml content did not recognized by template

I have xml with a tag which contains an attribute with a html content in it. I need to convert this html to xsl-fo . Here is my xslt code:
<xsl:template match ="rtf">
<fo:block-container>
<fo:block>
<xsl:call-template name ="ConvertHtmlToXslfo">
<xsl:with-param name ="content">
<xsl:value-of select ="#rtfAsHtml" disable-output-escaping ="yes"/>
</xsl:with-param>
</xsl:call-template>
</fo:block>
</fo:block-container>
</xsl:template>
<xsl:template name="ConvertHtmlToXslfo">
<xsl:param name ="content"></xsl:param>
<fo:block-container>
<xsl:apply-templates select="msxsl:node-set($content)"/> <!--here is the problem-->
</fo:block-container>
</xsl:template>
<xsl:template match ="div">
<fo:block-container>
<!--more code here-->
</fo:block-container>
</xsl:template>
<xsl:template match ="p">
<fo:block>
<!--more code here-->
</fo:block>
</xsl:template>
<xsl:template match ="span">
<fo:inline>
<!--more code here-->
</fo:inline>
</xsl:template>
But there is a problem, when in call apply-templates on this html content. the relevant templates doesn't recognize it.
Here is the xml Tag with Html attribute in it:
<rtf rtfAsHtml="<div ><p ><span>Hi!</span></p></div>"/>
Any idea how to convert this Html tag to xsl-fo ?
thank you!
The problem is that your xml/html content is escaped. You try to apply disable-output-escaping, but that only works upon writing to output file or stream. So, you are effectively just submitting the unescaped attribute contents against your templates, which doesn't do much indeed.
Not sure what kind of XSLT parser you are using, but if you use Saxon, you could try to apply saxon:parse:
http://saxonica.com/documentation9.4-demo/html/extensions/functions/parse.html
This does require the contents of the attribute to be well-formed. If not, you could try:
http://saxonica.com/documentation9.4-demo/html/extensions/functions/parse-html.html
HTH!