1

次の XML があります。

<sample>
    <value1>This is one</value1>
    <value2>Number two</value2>
    <value4>Last value</value4>
</sample>

Apache FOP/XSL-FO を使用して、次のような PDF が必要です。

Value 1: This is one Value 2: Number two
Value 3:                 Value 4: Last value

「Value 3:」と「Value 4:」の間のスペース/パディングに注意してください。

次の変換により、必要な結果が得られます。しかし、これは非常に複雑に思えます (多くの値を持つ実際の PDF ではうまく機能しない可能性があります)。

<xsl:stylesheet version="1.0"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                xmlns:fo="http://www.w3.org/1999/XSL/Format">

    <xsl:template match="sample">
        <fo:root>
            <fo:layout-master-set>
                <fo:simple-page-master master-name="page-layout">
                    <fo:region-body margin="10mm" region-name="body"/>
                </fo:simple-page-master>
            </fo:layout-master-set>
            <fo:page-sequence master-reference="page-layout">
                <fo:flow flow-name="body">
                    <fo:block>
                        <xsl:variable name="pad">                            
                            <xsl:choose>
                                <xsl:when test="value1">5</xsl:when>
                                <xsl:otherwise>25</xsl:otherwise>
                            </xsl:choose>
                        </xsl:variable>
                        <fo:inline padding-right="{$pad}mm">Value 1: <xsl:value-of select="value1"/></fo:inline>
                        Value 2: <xsl:value-of select="value2"/>
                    </fo:block>
                    <fo:block>
                        <xsl:variable name="pad">
                            <xsl:choose>
                                <xsl:when test="value3">5</xsl:when>
                                <xsl:otherwise>25</xsl:otherwise>
                            </xsl:choose>
                        </xsl:variable>
                        <fo:inline padding-right="{$pad}mm">Value 3: <xsl:value-of select="value3"/></fo:inline>
                        Value 4: <xsl:value-of select="value4"/>
                    </fo:block>
                </fo:flow>
            </fo:page-sequence>
        </fo:root>
    </xsl:template>

</xsl:stylesheet>

これを実装するためのより簡単な/より良い方法はありますか?

アップデート:

上記をテンプレート「フィールド」にリファクタリングしました。

<xsl:template name="field">
    <xsl:param name="txt"/>
    <xsl:param name="val"/>
    <xsl:param name="pad"/>
    <xsl:variable name="p">
        <xsl:choose>
            <xsl:when test="$val">5</xsl:when>
            <xsl:otherwise>
                <xsl:choose>
                    <xsl:when test="$pad"><xsl:value-of select="$pad"/></xsl:when>
                    <xsl:otherwise>25</xsl:otherwise>
                </xsl:choose>
            </xsl:otherwise>
        </xsl:choose>
    </xsl:variable>
    <fo:inline padding-right="{$p}mm"><xsl:value-of select="$txt"/>:</fo:inline>
    <fo:inline keep-with-previous="always" padding-right="5mm" font-weight="bold"><xsl:value-of select="$val"/></fo:inline>
</xsl:template>

次のように使用できます。

<xsl:call-template name="field">
    <xsl:with-param name="txt">Value 1</xsl:with-param>
    <xsl:with-param name="val"><xsl:value-of select="sample/value1"/></xsl:with-param>
</xsl:call-template>

テンプレートは、3 番目のオプション パラメータである pad を取ります。指定すると、その値がパディングとして使用されます。

David のテンプレート (受け入れられた回答を参照) は、必要に応じて padding-right 属性が上書きされる単純な if-contruct を使用します。

4

1 に答える 1

2

これはおそらくブラウザーで実行されていないため、xslt2 を使用しない理由はあります (これにより、かなり良くなります)。

しかし、これは少しリファクタリングされた XSLT 1 バージョンです。

<xsl:stylesheet version="1.0"
                xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                xmlns:fo="http://www.w3.org/1999/XSL/Format">

    <xsl:template match="sample">
        <fo:root>
            <fo:layout-master-set>
                <fo:simple-page-master master-name="page-layout">
                    <fo:region-body margin="10mm" region-name="body"/>
                </fo:simple-page-master>
            </fo:layout-master-set>
            <fo:page-sequence master-reference="page-layout">
                <fo:flow flow-name="body">
         <xsl:call-template name="twoval">
          <xsl:with-param name="a" select="value1"/>
          <xsl:with-param name="ahead" select="'Value 1'"/>
          <xsl:with-param name="b" select="value2"/>
          <xsl:with-param name="bhead" select="'Value 2'"/>
         </xsl:call-template>
         <xsl:call-template name="twoval">
          <xsl:with-param name="a" select="value3"/>
          <xsl:with-param name="ahead" select="'Value 3'"/>
          <xsl:with-param name="b" select="value4"/>
          <xsl:with-param name="bhead" select="'Value 4'"/>
         </xsl:call-template>
                </fo:flow>
            </fo:page-sequence>
        </fo:root>
    </xsl:template>


<xsl:template name="twoval">
<xsl:param name="a"/>
<xsl:param name="ahead"/>
<xsl:param name="b"/>
<xsl:param name="bhead"/>
<fo:block>
 <fo:inline padding-right="25mm">
  <xsl:if test="$a"><xsl:attribute name="padding-right">5mm</xsl:attribute></xsl:if>
  <xsl:value-of select="$ahead"/><xsl:text>: </xsl:text>
  <xsl:value-of select="$a"/>
 </fo:inline>
 <xsl:text> </xsl:text>
 <xsl:value-of select="$bhead"/><xsl:text>: </xsl:text>
 <xsl:value-of select="$b"/>
</fo:block>
</xsl:template>

</xsl:stylesheet>
于 2012-09-15T11:37:47.437 に答える