Reputation: 1816
I want to create an element by matching @pagebreak. @pagebreak is appearing with multiple parent like para, table, etc...
INPUT XML:
<?xml version="1.0" encoding="UTF-8"?>
<root>
<child1>
<para>This is first para.</para>
<para pagebreak="yes">This is second para.</para>
<para>This is first para.</para>
<table>
<tr>
<td>first table</td>
</tr>
</table>
</child1>
<child1>
<para>This is first para.</para>
<para>This is second para.</para>
<para>This is first para.</para>
<table pagebreak="yes">
<tr>
<td>second table</td>
</tr>
</table>
</child1>
</root>
CURRENT OUTPUT:
<?xml version="1.0" encoding="UTF-8"?>
<article>
<section>
<p class="p_1">This is first para.</p>
<div>
<pagebreak type="yes"/>
</div>
<para>This is second para.</para>
<p class="p_3">This is first para.</p>
<table id="tab_1">
<tr>
<td>first table</td>
</tr>
</table>
</section>
<section>
<p class="p_1">This is first para.</p>
<p class="p_2">This is second para.</p>
<p class="p_3">This is first para.</p>
<div>
<pagebreak type="yes"/>
</div>
<table>
<tr>
<td>second table</td>
</tr>
</table>
</section>
</article>
DESIRED OUTPUT:
<?xml version="1.0" encoding="UTF-8"?>
<article>
<section>
<p class="p_1">This is first para.</p>
<div>
<pagebreak type="yes"/>
</div>
<p class="p_2">This is second para.</p>
<p class="p_3">This is first para.</p>
<table id="tab_1">
<tr>
<td>first table</td>
</tr>
</table>
</section>
<section>
<p class="p_1">This is first para.</p>
<p class="p_2">This is second para.</p>
<p class="p_3">This is first para.</p>
<div>
<pagebreak type="yes"/>
</div>
<table id="tab_2">
<tr>
<td>second table</td>
</tr>
</table>
</section>
</article>
template for element/@pagebrake
should be applied same as without @pagebrake
.
NOTE: In output you can see that:
<para>This is second para.</para>
is not converted as
para template rules. <table>
is not converted as
table template rules.XSLT I've USED:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="xs" version="2.0">
<xsl:output indent="yes"/>
<xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="root">
<article>
<xsl:apply-templates select="@* | node()"/>
</article>
</xsl:template>
<xsl:template match="para">
<p class="{concat('p_', count(preceding-sibling::para)+1)}">
<xsl:apply-templates select="@* | node()"/>
</p>
</xsl:template>
<xsl:template match="child1|child2">
<section>
<xsl:apply-templates select="@* | node()"/>
</section>
</xsl:template>
<xsl:template match="table">
<xsl:variable name="num"><xsl:number/></xsl:variable>
<table id="{concat('tab_', $num)}">
<xsl:apply-templates select="@* | node()"/>
</table>
</xsl:template>
<xsl:template match="*[@pagebreak]">
<div><pagebreak type="yes"/></div>
<xsl:copy>
<xsl:apply-templates/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
Upvotes: 0
Views: 29
Reputation: 70648
The problem is in your template matching *[@pagebreak]
. Instead of doing xsl:apply-templates
, you should do xsl:next-match
so that the current node is continued to be matched, rather than going on to its child.
<xsl:template match="*[@pagebreak]">
<div><pagebreak type="yes"/></div>
<xsl:next-match />
</xsl:template>
You would also need to add a template to stop @pagebreak
being output too.
<xsl:template match="@pagebreak" />
Upvotes: 1