Question

First of all, I'm trying to create a PDF from an XML with help of XSLT, XPath and XSL-FO.

I have an XML with multiple footnotes and I use a template to render them automatically after tag name "note".

XML:

<document>  
  <ul type='custom-list-1' startdist="0.5cm" gap="0.15cm">
    <li space-before="30pt">
        List-item 1
        <block margin-left="-15pt" margin-right="-15pt" text-align="center">
            <table layout="fixed" width="100%">
                <col number="1" width="30%" />
                <col number="2" width="17%" />
                <col number="3" width="17%" />
                <col number="4" width="17%" />
                <col number="5" width="17%" />                      
                <tbody>
                    <tr font-style="italic">
                        <th>sample title</th>
                        <th colspan="4">sample title</th>
                    </tr>                       
                    <tr>
                        <td>
                            Bla bla bla
                            <note name="name-1">
                                Footnote for "bla bla bla"
                            </note>
                        </td>
                        <td colspan="4">
                            .............
                        </td>
                    </tr>                   
                    <tr>
                        <td>
                            Comision Administrare Online Banking
                        </td>
                        <td colspan="4">
                            .........
                        </td>
                    </tr>
                    <tr>
                        <td>
                            Another... Bla bla bla
                            <note name="name-2">
                                Footnote for "Another... Bbla bla bla"
                            </note>
                        </td>
                        <td colspan="4">
                            ......
                        </td>
                    </tr>                       
                </tbody>                
            </table>                            
        </block>
    </li>
    <li space-before="30pt">List-item 2:        

        <block margin-left="-15pt" text-align="center">
            <table layout="fixed" width="100%">
                <col number="1" width="18%" />
                <col number="2" width="13%" />
                <col number="3" width="13%" />
                <col number="4" width="16%" />                  
                <col number="5" width="13%" />
                <col number="6" width="13%" />
                <col number="7" width="13%" />
                <tbody>
                    <tr font-style="italic">
                        <th colspan="2" rowspan="2">Sample title</th>
                        <th colspan="2">Sample title</th>                       
                        <th rowspan="2">Sample title</th>
                        <th rowspan="2">Sample title</th>
                        <th rowspan="2">Sample title</th>
                    </tr>
                    <tr font-style="italic">
                        <th>Min</th>
                        <th>Max</th>
                    </tr>                       
                    <tr>                            
                        <td colspan="2">Some text here</td>
                        <td colspan="2">
                            1%
                            <note name="name-3">
                                Footnote for "1%"
                            </note>
                            / 0.5%
                            <note name="name-4">
                                Footnote for "0.5%"
                            </note>
                        </td>
                        <td>-</td>
                        <td>-</td>
                        <td>-</td>                          
                    </tr>                       
                    <tr>                            
                        <td colspan="2">Sample text</td>
                        <td colspan="2">
                            1%
                            <note name="name-3">
                                Footnote for "1%"
                            </note>
                            / 0.5%
                            <note name="name-4">
                                Footnote for "0.5%"
                            </note>
                        </td>
                        <td>-</td>
                        <td>-</td>
                        <td>-</td>                          
                    </tr>                       
                    <tr>                            
                        <td colspan="2">Sample text</td>
                        <td colspan="2">
                            1%
                            <note name="name-3">
                                Footnote for "1%"
                            </note>
                            / 0.5%
                            <note name="name-4">
                                Footnote for "0.5%"
                            </note>
                        </td>
                        <td>-</td>
                        <td>-</td>
                        <td>-</td>                          
                    </tr>                       
                </tbody>
            </table>
        </block>
    </li>
    <li space-before="30pt">List-item 3
        <block margin-left="-15pt" text-align="center">
            <table layout="fixed" width="100%">
                <col number="1" width="25%" />
                <col number="2" width="15%" />
                <col number="3" width="15%" />
                <col number="4" width="22%" />
                <col number="5" width="22%" />                      
                <tbody>
                    <tr font-style="italic">
                        <th colspan="2">Sample title</th>
                        <th></th>
                        <th>Sample title</th>
                        <th>Sample title</th>
                    </tr>
                    <tr>                            
                        <td colspan="2">Sample text</td>                            
                        <td></td>
                        <td>0%</td>
                        <td>0%</td>
                    </tr>
                    <tr>                            
                        <td colspan="2">Sample text</td>                            
                        <td></td>
                        <td>0.05%<note name="name-5">Footnote for "0.05%"</note></td>
                        <td>0.05%</td>
                    </tr>                       
                    <tr>                            
                        <td colspan="2">Sample text</td>                            
                        <td></td>
                        <td>0%</td>
                        <td>0%</td>
                    </tr>
                </tbody>
            </table>

        </block>
    </li>       
</ul>

XSLT:

<xsl:attribute-set name="note.data" >
    <xsl:attribute name="text-align">justify</xsl:attribute>        
    <xsl:attribute name="font-weight">normal</xsl:attribute>
</xsl:attribute-set>

<xsl:key name="by-name" match="//note[@name]" use="@name" />

<xsl:template match="note">
    <xsl:call-template name="note" />
</xsl:template>

<xsl:template name="note">
    <xsl:param name="unique-elements" 
       select="current()[generate-id(.) = generate-id(key('by-name', @name)[1])]"/>     
    <xsl:param name="identical-elements" 
       select="current()[not(generate-id(.) = generate-id(key('by-name', @name)[1]))]"/>

    <xsl:if test="$unique-elements">
        <xsl:variable name="element" select="$unique-elements"/>

        <fo:footnote>       
            <fo:inline baseline-shift="super" font-size="75%" color="red">
                <xsl:number level="any" count="//note[generate-id(.) = generate-id(key('by-name', @name)[1])]" format="(1)" />
            </fo:inline>

            <fo:footnote-body xsl:use-attribute-sets="note.data">   
                <fo:block color="blue">                             
                    <fo:inline baseline-shift="super" font-size="75%">
                        <xsl:number level="any" count="//note[generate-id(.) = generate-id(key('by-name', @name)[1])]" format="(1)" />
                    </fo:inline>
                    <xsl:value-of select="$element" />                                              
                </fo:block>
            </fo:footnote-body>
        </fo:footnote>          
    </xsl:if>           

    <xsl:if test="$identical-elements">
        <fo:inline baseline-shift="super" font-size="75%" color="green">
            <xsl:number level="any" count="//note[generate-id(.) = generate-id(key('by-name', @name)[1])]" format="(1)" />
        </fo:inline>            
    </xsl:if>
</xsl:template>

PDF output:

enter image description here

So, I managed to suppress the identical footnotes and maintain the count of the unique footnotes (in image colored with red) and add the last count value for the identical footnotes (in image colored with green).

The problem now is that I can't figure it out how can I maintain the same count value for the identical footnotes.

Thanks in advance!

Était-ce utile?

La solution

So here is a solution, but without using xsl:number, that usually gives me too much of a headache, but since you have been using level="any" it doesn't really matter:

<xsl:template match="note">
    <!-- 
        counts unique preceding notes starting from first note with current @name
    -->
    <xsl:variable name="number"
        select="count((//note[@name=current()/@name])[1]/preceding::note[not(@name=../preceding::note/@name)]) + 1"/>

    <xsl:choose>
        <!-- if there is no preceding note with same name -->
        <xsl:when test="not(preceding::note/@name=current()/@name)">
            <fo:footnote>
                <fo:inline baseline-shift="super" font-size="75%" color="red">(<xsl:value-of
                        select="$number"/>)</fo:inline>

                <fo:footnote-body>
                    <fo:block color="blue">
                        <xsl:if test="@margin-left">
                            <xsl:attribute name="margin-left">
                                <xsl:value-of select="@margin-left"/>
                            </xsl:attribute>
                        </xsl:if>
                        <fo:inline baseline-shift="super" font-size="75%">(<xsl:value-of select="$number"
                            />)</fo:inline>
                        <xsl:value-of select="."/>
                    </fo:block>
                </fo:footnote-body>

            </fo:footnote>
        </xsl:when>
        <xsl:otherwise>
            <fo:inline baseline-shift="super" font-size="75%" color="red">(<xsl:value-of
                    select="$number"/>)</fo:inline>
        </xsl:otherwise>
    </xsl:choose>


</xsl:template>

Autres conseils

The best way would be to group the identical notes and then select the first one from each group. With XSLT 2.0 you can use the group-by atribute. In XSLT 1.0 you can do this creating a key for all notes:

<xsl:key name="notes" match="//note" use="@name"/>

And then calling your template using the predicate shown below:

<xsl:template match="parent-element">
...
     <xsl:apply-templates select="note[generate-id(.) = generate-id( key('notes', @name)[1])]" />
...
</xsl:template>

The expression compares the current note (.) with the first item in the group of notes with the same @name, so you are selecting the first item of each group.

You will also have to fix your node-count and restrict it to the reduced set (since it is counting all nodes including the duplicate ones):

note[generate-id(.) = generate-id( key('notes', @name)[1])]

If you are using AH Formatter, you can suppress duplicate footnotes on the same page by using the aptly named axf:suppress-duplicate-footnote extension property. See https://www.antennahouse.com/product/ahf64/ahf-ext.html#axf.suppress-duplicate-footnote and the "Footnote arrangement in the column document (axf:footnote-position)" sample from https://www.antennahouse.com/antenna1/comprehensive-xsl-fo-tutorials-and-samples-collection/

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top