2010-12-12 77 views
1

je voudrais produire un h1 tag h3 pour un en-tête en fonction de sa position de sectionétiquette d'en-tête en fonction de la position dans xml

le xml est au format

<sections> 
     <section> 
      <header>section 1 header</header> 
      <image alt="section 1 image alt">imagename.filetype</image> 
      <content>section 1 content</content> 
     </section> 
     <section> 
      <header>section 2 header</header> 
      <image alt="section 2 image alt">imagename.filetype</image> 
      <content>section 2 content</content> 
     </section> 
     <section> 
      <header>section 3 header</header> 
      <image alt="section 3 image alt">imagename.filetype</image> 
      <content>section 3 content</content> 
     </section> 
    </sections> 

ma sortie voudrait être comme

<div> 
<h1> section 1 header</h1> 
<img alt="section 1 image alt" src="imagename.filename"/> 
section 1 content 
</div> 

<div> 
<h2> section 2 header</h2> 
<img alt="section 2 image alt" src="imagename.filename"/> 
section 2 content 
</div> 

<div> 
<h3> section 3 header</h3> 
<img alt="section 3 image alt" src="imagename.filename"/> 
section 3 content 
</div> 

est-il un moyen simple de faire cela? des idées appréciées!

genre grâce Treemonkey

mise à jour:

<xsl:template mode="section" match="section">  
     <xsl:apply-templates mode="header" select="header"> 
      <xsl:with-param name="position">h<xsl:value-of select="position()"/></xsl:with-param> 
     </xsl:apply-templates> 
     <img alt="{image/@alt}" src="{image}" /> 
     <xsl:value-of select="content"/> 
    </xsl:template> 

    <xsl:template mode="header" match="header"> 
    <xsl:param name="position">0</xsl:param> 
     <xsl:element name="{$position}"><xsl:value-of select="."/></xsl:element>  
    </xsl:template> 

utilisant le xslt ci-dessus qui est la version légèrement mise à jour du post Khachik

+0

Bonne question, +1. Voir ma réponse pour une solution complète qui est complètement dans l'esprit de XSLT (style push). :) –

Répondre

2

Voici une solution complète qui est tout à fait dans le style push:

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
<xsl:output omit-xml-declaration="yes" indent="yes"/> 
<xsl:strip-space elements="*"/> 

<xsl:template match="node()|@*"> 
    <xsl:copy> 
     <xsl:apply-templates select="node()|@*"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="section"> 
    <div> 
    <xsl:apply-templates/> 
    </div> 
</xsl:template> 

<xsl:template match="header"> 
    <xsl:element name="h{count(../preceding-sibling::section)+1}"> 
    <xsl:apply-templates/> 
    </xsl:element> 
</xsl:template> 
<xsl:template match="sections|content"> 
    <xsl:apply-templates/> 
</xsl:template> 
</xsl:stylesheet> 

lorsque cette transformation est appliquée sur le document XML fourni:

<sections> 
    <section> 
     <header>section 1 header</header> 
     <image alt="section 1 image alt">imagename.filetype</image> 
     <content>section 1 content</content> 
    </section> 
    <section> 
     <header>section 2 header</header> 
     <image alt="section 2 image alt">imagename.filetype</image> 
     <content>section 2 content</content> 
    </section> 
    <section> 
     <header>section 3 header</header> 
     <image alt="section 3 image alt">imagename.filetype</image> 
     <content>section 3 content</content> 
    </section> 
</sections> 

la recherché, correcte le résultat est produit:

<div> 
     <h1>section 1 header</h1> 
     <image alt="section 1 image alt">imagename.filetype</image> 
section 1 content 
    </div> 
    <div> 
     <h2>section 2 header</h2> 
     <image alt="section 2 image alt">imagename.filetype</image> 
section 2 content 
    </div> 
    <div> 
     <h3>section 3 header</h3> 
     <image alt="section 3 image alt">imagename.filetype</image> 
section 3 content 
    </div> 
+0

Merci pour cela juste ce que j'étais après!, Ne le comprends pas pour le moment, mais va le résoudre. ah donc ça compte les en-têtes avant une addition 1. tu as merci Dimitre – Treemonkey

+0

+1 Bonne réponse. Il correspondrait exactement à la sortie désirée en ajoutant une règle pour 'image' et même en supprimant la règle d'indentité et la règle écrasant la règle intégrée pour les éléments. –

0

Ce pas une réponse car il semble laid, mais est trop long pour un commentaire. Je ne suis pas sûr que ce soit la meilleure façon de le faire, mais:

<xsl:template match="section"> 
    <xsl:apply-templates select="./header"> 
     <xsl:with-param name="position"><xsl:value-of select="position()"/> 
     </xsl:with-param> 
    </xsl:apply-templates> 
    <!-- section stuff here --> 
</xsl:template> 

<xsl:template match="header"> 
    <xsl:param name="position">0</xsl:param> 
    <xsl:variable name="tagname"><xsl:value-of select="concat('h', $position)"></xsl:value-of></xsl:variable> 
    <xsl:element name="{$tagname}"><xsl:value-of select="."/></xsl:element> 
</xsl:template> 

Une note: Je ne pense pas à la tête en fonction de la position est une bonne idée. DocBook et d'autres langues utilisent le niveau de section pour placer la balise d'en-tête appropriée.

+0

ceci est similaire à mon idée originale peut l'essayer avec un peu éditer :) – Treemonkey