Search code examples
xsl-foapache-fop

How can I create a two column layout with XSL-FO and FOP 1.0?


I've got a piece of software that creates an XSL-FO description from a text file and converts that into a PDF document. Each line in the text file is converted to a fo:block in FO, which sounds wrong, but I cannot change that right now. My document contains 1 to 3 pages of A4.

What I now need to do is add a graphic that is about 8cm in width below the existing text. It should be left-aligned. Next to it I want to place a block of text with a (long) description.

Layout example

I've looked at a couple of documentations for FO and came up with this:

<fo:block intrusion-displace="block" margin-top="20mm">
 <fo:float float="right">
   <fo:block margin-left="20mm">
    Bacon ipsum dolor sit amet laborum proident...
   </fo:block>
 </fo:float> 
  <fo:external-graphic src="image.png"/> 
</fo:block>

This seemed to be what I wanted (after some fine-tuning of course), but unfortunately FOP does not support fo:float yet.

There also seems to be a way to create multiple columns (without a table), but I have not been able to figure out how that works. One seems to need a new page for that, but I need to use the current page if there is space available (which I do not have to care about I guess).

So my question: Is there another way to build this without using fo:float?


Solution

  • You can try to use the image as a background image and leave a left padding that is as wide as the image.

    <fo:block intrusion-displace="block" margin-top="20mm">
       <fo:block padding-left="20mm" 
           background-image="image.png" 
           background-repeat="no-repeat">
        Bacon ipsum dolor sit amet laborum proident...
       </fo:block>
    </fo:block>
    

    If the image needs further treatment that is only possible with <fo:external-graphic>, you could use the padding technique and an additional, absolutely positioned block-container:

    <fo:block intrusion-displace="block" margin-top="20mm">
       <fo:block padding-left="20mm">
        Bacon ipsum dolor sit amet laborum proident...
       </fo:block>
       <fo:block-container absolute-position="absolute">
           <fo:block>
              <fo:external-graphic src="image.png"/>
           </fo:block>
       </fo:block-container>
    </fo:block>
    

    A third option would be to use a table.