Page 1 of 1

How to continue the numbering of the previous list

Posted: Fri Jan 06, 2017 6:56 pm
by kris
Hi all,

Imagine that I have two ordered lists, and some text in between.
Is there any chance to continue the numbering of the first list in the second one?

Thanks,
Kris

Re: How to continue the numbering of the previous list

Posted: Mon Jan 09, 2017 5:47 pm
by radu_pisoi
Hi,

What output format are you trying to customize? PDF or HTML?

Re: How to continue the numbering of the previous list

Posted: Mon Jan 09, 2017 6:00 pm
by kris
radu_pisoi wrote:Hi,

What output format are you trying to customize? PDF or HTML?
PDF.

Thanks,
Kris

Re: How to continue the numbering of the previous list

Posted: Tue Jan 10, 2017 8:24 pm
by radu_pisoi
Hi,

Yes, I think it is possible by extending the default processing with a PDF customization plugin.

The list item numbering is implemented in the following XSLT stylesheet:

Code: Select all

{DITA-OT-folder}/plugins/org.dita.pdf2/xsl/fo/lists.xsl
More precisely, in the template:

Code: Select all

<xsl:template match="*[contains(@class, ' topic/ol ')]/*[contains(@class, ' topic/li ')]">
...
<xsl:choose>
<xsl:when test="parent::*[contains(@class, ' topic/ol ')]/parent::*[contains(@class, ' topic/li ')]/parent::*[contains(@class, ' topic/ol ')]">
<xsl:number format="a"/>
</xsl:when>
<xsl:otherwise>
<xsl:number/>
</xsl:otherwise>
</xsl:choose>
...
</xsl:template>


I think you should overwrite the above template in your customization and generate a certain number for your use case.

However, a better place to address questions like this is DITA users list. This list is monitored by many DITA specialists, so the chances to get a fast and good answer are higher. We are also registered and active to this list.

Re: How to continue the numbering of the previous list

Posted: Tue Mar 14, 2017 7:54 pm
by kris
Hi Radu,

thanks for the pointer, I managed to resolve it for PDF.
Now I need to do the same for XHTML.

I think the definition of how to handle lists is in the plugins/myplugin/xsl/xslhtml/dita2htmlImpl.xsl file, right?

I couldn't figure out how that works. The ol template seems only to set some attributes.
The list item handler calls this function:

Code: Select all

<xsl:attribute name="id" select="dita-ot:get-prefixed-id($idvalue/parent::*, $idvalue)"/>
... and then...

Code: Select all

<xsl:function name="dita-ot:get-prefixed-id" as="xs:string">
<xsl:param name="element" as="element()"/>
<xsl:param name="id" as="xs:string"/>
<xsl:sequence select="dita-ot:generate-id($element/ancestor::*[contains(@class, ' topic/body ')][1]/parent::*/@id, $id)"/>
</xsl:function>
What does this do? Am I looking at the right spot to manipulate the numbering for XHTML?

Thanks,
Kris

Re: How to continue the numbering of the previous list

Posted: Fri Mar 17, 2017 3:30 pm
by Radu
Hi,

The dita2htmlImpl.xsl indeed seems to have a template which outputs the OL:

Code: Select all

<xsl:template match="*[contains(@class, ' topic/ol ')]" name="topic.ol">
...............
The XHTML <ol> element has a special start attribute which can be set to a certain number from which the counter should start.
So you can look at the sibling of the ol and find the start number for the current ol.
You can also set a special @outputclass value on the <ol>s for which you want to continue the numbering of the previous ones, just so that you can differentiate in the XSLT between consecutive OLs on which you want to reset the counter and consecutive ols for which you want to continue counting from the previous ol.

Regards,
Radu

Re: How to continue the numbering of the previous list

Posted: Mon Mar 20, 2017 2:23 pm
by kris
Hi Radu,

thanks for the suggestions.

I'm not sure what I'm doing wrong, but the script doesn't seem to enter my <if>. I added it inside the <ol>. I'm not sure how to check there if the original tag had the outputclass attribute set to 'continue':

Code: Select all

<xsl:template match="*[contains(@class, ' topic/ol ')]" name="topic.ol">
<xsl:variable name="olcount" select="count(ancestor-or-self::*[contains(@class, ' topic/ol ')])"/>
<xsl:apply-templates select="*[contains(@class, ' ditaot-d/ditaval-startprop ')]" mode="out-of-line"/>
<xsl:call-template name="setaname"/>
<ol>
<xsl:call-template name="commonattributes"/>
<xsl:if test="parent::*[contains(@outputclass, 'continue')]"> <!-- If we need to continue the previous list. Works with one-level lists only. -->
<xsl:attribute name="start">
<xsl:value-of select="count(preceding-sibling::*[contains(@class, ' topic/ol ')]/child::*[contains(@class, ' topic/li ')])"/> <!-- Calculating the last number of the previous list. -->
</xsl:attribute>
</xsl:if>
<xsl:apply-templates select="@compact"/>
<xsl:choose>
<xsl:when test="$olcount mod 3 = 1"/>
<xsl:when test="$olcount mod 3 = 2"><xsl:attribute name="type">a</xsl:attribute></xsl:when>
<xsl:otherwise><xsl:attribute name="type">i</xsl:attribute></xsl:otherwise>
</xsl:choose>
<xsl:call-template name="setid"/>
<xsl:apply-templates/>
</ol>
<xsl:apply-templates select="*[contains(@class, ' ditaot-d/ditaval-endprop ')]" mode="out-of-line"/>
<xsl:value-of select="$newline"/>
</xsl:template>
What am I doing wrong?

Thanks in advance for the help,
Kris

Re: How to continue the numbering of the previous list

Posted: Mon Mar 20, 2017 4:39 pm
by Radu
Hi Kris,

In the Oxygen Preferences->DITA page you can choose to always show the console output.
Then if you add xsl:messages in your XSLT scripts, they will appear in the DITA OT console view while the publishing is done so you can use those messages for debugging.
In your case the template matches directly the <ol> element. Using the XPath parent::*[contains(@outputclass, 'continue')] you seem to be looking at the parent of the <ol> element for the @outputclass attribute. Shouldn't you be looking directly on the current <ol> element for that attribute?
The second XPath you are using looks OK. You can debug its value with something like:

Code: Select all

<xsl:message>Start value <xsl:value-of select="count(preceding-sibling::*[contains(@class, ' topic/ol ')]/child::*[contains(@class, ' topic/li ')])"/></xsl:message>
Regards,
Radu

Re: How to continue the numbering of the previous list

Posted: Mon Mar 20, 2017 6:59 pm
by kris
Hi again,

thanks for the quick answer. The parent:: was just a try to resolve this, I already tested without and did not work.
Now I looked at the code of the output and for some reason I see this:

Code: Select all

<ol class="ol continue">
...
</ol>
Is this the normal behaviour? Not sure why it is an attribute called class...

Anyhow, I changed my <if> to the following, but it still has no effect:

Code: Select all

<xsl:if test="*[contains(@class, 'ol continue')]">
<xsl:attribute name="start">
<xsl:value-of select="count(preceding-sibling::*[contains(@class, ' topic/ol ')]/child::*[contains(@class, ' topic/li ')])"/>
</xsl:attribute>
</xsl:if>
Any suggestion is very welcome.
Kris

Re: How to continue the numbering of the previous list

Posted: Tue Mar 21, 2017 9:58 am
by Radu
Hi Kris,
Now I looked at the code of the output and for some reason I see this...
Whenever you set the @outputclass attribute on a DITA element, in the XHTML output it is converted to a @class="... customvalue..." so that it can be easily matched using CSS. So this is normal.
The XSLT template you are changing is part of the set of stylesheets which are matching the DITA elements and produces the XHTML output so in your XSLT template you must match the DITA element and its @outputclass attribute.
Anyhow, I changed my <if> to the following, but it still has no effect:
You first need to see if your changes are taken into account at all.

For example this XSLT template change works for me:

Code: Select all

<xsl:template match="*[contains(@class, ' topic/ol ')]" name="topic.ol">
<xsl:message>MATCH <xsl:copy-of select="."></xsl:copy-of></xsl:message>
<xsl:variable name="olcount" select="count(ancestor-or-self::*[contains(@class, ' topic/ol ')])"/>
<xsl:apply-templates select="*[contains(@class, ' ditaot-d/ditaval-startprop ')]" mode="out-of-line"/>
<xsl:call-template name="setaname"/>
<ol>
<xsl:call-template name="commonattributes"/>
<xsl:if test="contains(@outputclass, 'continue')"> <!-- If we need to continue the previous list. Works with one-level lists only. -->
<xsl:attribute name="start">
<xsl:value-of select="count(preceding-sibling::*[contains(@class, ' topic/ol ')]/child::*[contains(@class, ' topic/li ')]) + 1"/> <!-- Calculating the last number of the previous list. -->
</xsl:attribute>
</xsl:if>
<xsl:apply-templates select="@compact"/>
<xsl:choose>
<xsl:when test="$olcount mod 3 = 1"/>
<xsl:when test="$olcount mod 3 = 2"><xsl:attribute name="type">a</xsl:attribute></xsl:when>
<xsl:otherwise><xsl:attribute name="type">i</xsl:attribute></xsl:otherwise>
</xsl:choose>
<xsl:call-template name="setid"/>
<xsl:apply-templates/>
</ol>
<xsl:apply-templates select="*[contains(@class, ' ditaot-d/ditaval-endprop ')]" mode="out-of-line"/>
<xsl:value-of select="$newline"/>
</xsl:template>
I added an xsl:message on the first line of the template and after publishing I looked in the DITA OT console output view to see if my changed template is getting called.
If you do the same on your side and discover your template is not getting called, then there is a problem with your plugin overriding this particular XSLT template.

Regards,
Radu