XSL-FO試行錯誤 リストアイテムのインデントが効いていない?

改まった内容の記事は結構時間がかかりますが、このブログ連載のタイトルが「試行錯誤」なので、凡ミスを載せたりしても良いかな、ということで。
実際に起こった失敗より、一部改変しています。

XSLTで箇条書きにする変換を書いていたときのこと。

FOに変換後、PDF出力すると一部のリストブロックだけ箇条書きのラベルの上に箇条書きの内容が。
これ自体はインデントの指定を間違ったときにすぐ起こるので、あまり悩むことはありません。どこかでアイテムラベルかアイテムボディのインデント指定を上書きしてしまったのでしょう。

しかし、アイテムラベルやアイテムボディの周辺を見回しても特に不味いところは見当りません。仕様を把握している方は「ああ、それは多分……」とこの時点で見当がついたかもしれません。

それでは次のようなコードで、どんなことが起こり得るでしょうか?

<xsl:attribute-set name="atsList">
  <xsl:attribute name="provisional-distance-between-starts">ホニャララ</xsl:attribute>
  <xsl:attribute name="provisional-distance-label-separation">フガフガ</xsl:attribute>
</xsl:attribute-set>
<xsl:attribute-set name="atsListLabel">
  <xsl:attribute name="start-indent">いいかんじ</xsl:attribute>
  <xsl:attribute name="end-indent">label-end()</xsl:attribute>
</xsl:attribute-set>

<xsl:attribute-set name="atsListBody">
  <xsl:attribute name="start-indent">body-start()</xsl:attribute>
  <xsl:attribute name="end-indent">ほどほど</xsl:attribute>
</xsl:attribute-set>


<xsl:template ...>
  <fo:list-block xsl:use-attribute-sets="atsList">
    <fo:list-item>
      <fo:list-item-label
       xsl:use-attribute-sets="atsListLabel">
        <fo:block xsl:use-attribute-sets="atsListLabelBlock">
          LABEL
        </fo:block>
      </fo:list-item-label>
      <fo:list-item-body xsl:use-attribute-sets="atsListBody">
        <xsl:apply-templates select="ナンチャラ"/>
      </fo:list-item-body>
    </fo:list-item>
  </fo:list-block>
</xsl:template>

答え合わせにいきましょう。

<!-- 変換後のFO -->
      <fo:list-item-body start-indent="body-start()" ... > 
        <fo:block start-indent="0pt" >
        ...
        </fo:block>
      </fo:list-item-body> 

実際に問題の指定があったのはこの箇所ではなく<xsl:apply-templates>の先、アイテムボディの内容を記述するブロックでした。start-indent="0pt"の指定があるブロックへ変換していた箇所があったのです。XSLTでattribute-setを分けていたため、気づくのが遅れました。それでも変換結果のFOを確認しながら作業していればもっと早くに気づけたのではないかと思います。

設計するときは、小さなテストケースや検証環境をあらかじめ用意しましょう。ホントに。




PDF Viewer SDK
PDF表示と編集ライブラリ


PDF Tool API
PDF 編集・加工ライブラリ!


HTML on Word
WebページをWordで作る!


アウトライナー
PDFを解析して しおり・目次を自動生成