[xep-support] Re: inserting pdf documents, OK, a new CoolTool

Kevin Brown kevin at renderx.com
Wed Jul 22 12:27:17 PDT 2015


Charles:

 

I haven’t fully tested, but something like this would work:

 

Given this FO with PIs for documents to be inserted:

 

<fo:root xmlns:fo="http://www.w3.org/1999/XSL/Format"
            xmlns:rx="http://www.renderx.com/XSL/Extensions">
            <fo:layout-master-set>
                        <fo:simple-page-master margin="1in" page-width="8.5in" page-height="11in"
                                    master-name="first">
                                    <fo:region-body margin="0in" border="1pt solid black"/>
                        </fo:simple-page-master>
            </fo:layout-master-set>
            <fo:page-sequence master-reference="first">
                        <?xep-insert-document file:/C:/Users/kbrown01/Desktop/RXTest/doc1.pdf?>
                        <?xep-insert-document file:/C:/Users/kbrown01/Desktop/RXTest/doc2.pdf?>
                        <?xep-insert-document file:/C:/Users/kbrown01/Desktop/RXTest/doc3.pdf?>
                        <fo:flow flow-name="xsl-region-body">
                                    <fo:block>
                                                content
                                    </fo:block>
                        </fo:flow>
            </fo:page-sequence>
</fo:root>

 

If you format to XEPOUT, you get:

 

<xep:document xmlns:xep="http://www.renderx.com/XEP/xep" producer="XEP 4.24.395" creator="Unknown" author="Unknown" title="Untitled">
<xep:page width="612000" height="792000" page-number="1" page-id="1"><?xep-insert-document file:/C:/Users/kbrown01/Desktop/RXTest/doc1.pdf?>
<?xep-insert-document file:/C:/Users/kbrown01/Desktop/RXTest/doc2.pdf?>
<?xep-insert-document file:/C:/Users/kbrown01/Desktop/RXTest/doc3.pdf?>

…

</xep:page>
</xep:document>

 

So you could use this XSL:

 

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xep="http://www.renderx.com/XEP/xep" 
    version="1.0"> 
    <xsl:template match="@* | node()">
        <xsl:copy>
            <xsl:apply-templates select="@*"/>
            <xsl:apply-templates select="node()"/>
        </xsl:copy>
    </xsl:template>
    <!-- Create xep-insert-document elements before the xep:page -->
    <xsl:template match="xep:page[processing-instruction('xep-insert-document')]">
        <xsl:for-each select="processing-instruction('xep-insert-document')">
            <xep:insert-document>
                <xsl:attribute name="src">
                    <xsl:value-of select="."/>
                </xsl:attribute>
            </xep:insert-document>
        </xsl:for-each>
        <xsl:copy>
            <xsl:apply-templates select="@*"/>
            <xsl:apply-templates select="node()"/>
        </xsl:copy>
    </xsl:template>
    <xsl:template match="processing-instruction('xep-insert-document')"/>
</xsl:stylesheet>

 

Yields this:

 

<xep:document xmlns:xep="http://www.renderx.com/XEP/xep" producer="XEP 4.24.395" creator="Unknown"
    author="Unknown" title="Untitled">
    <xep:insert-document src="file:/C:/Users/kbrown01/Desktop/RXTest/doc1.pdf"/>
    <xep:insert-document src="file:/C:/Users/kbrown01/Desktop/RXTest/doc2.pdf"/>
    <xep:insert-document src="file:/C:/Users/kbrown01/Desktop/RXTest/doc3.pdf"/>
    <xep:page width="612000" height="792000" page-number="1" page-id="1">
…
    </xep:page>
</xep:document>

 

 

 

From: Charles Porter [mailto:charles.b.porter at rrd.com] 
Sent: Wednesday, July 22, 2015 10:32 AM
To: Kevin Brown <kevin at renderx.com>
Cc: RenderX Community Support List <xep-support at renderx.com>
Subject: Re: [xep-support] inserting pdf documents, OK, a new CoolTool

 

The page counts of the inserted documents are variable.  The two documents to insert are drawn from a large pool provided by a third party, and must include all pages.

 

I did not know about <xep:insert-document/>. That looks promising, since we have no requirement to keep track of pages for accurate page numbers.

 

Thanks for your help.




________________________________________________________________________

Charles B. Porter | Technical Analyst, Customer Facing Systems | RR Donnelley

655 Brighton Beach Rd | Menasha, WI 54952
Office: 920.751.7612 | Mobile: 920.450.3480 | Fax: 920.751.7686
charles.b.porter at rrd.com <mailto:charles.b.porter at rrd.com> 
http://www.rrdonnelley.com <http://rrdonnelley.com> 

 

On Wed, Jul 22, 2015 at 12:19 PM, Kevin Brown <kevin at renderx.com <mailto:kevin at renderx.com> > wrote:

Charles:

 

Is it that you do not know the page count in the second document or it is variable? 

That would be the only way that it would not work. Because you could just do this (if it was five pages):

<fo:page-sequence master-reference="ins1" rx:insert-document="url(some_url)">

    <fo:flow flow-name="xsl-region-body">

<fo:block line-height="0pt">

                    <fo:external-graphic rx:pdf-page="1" src="doc2.pdf"/>

                </fo:block>

                <fo:block line-height="0pt">

                    <fo:external-graphic rx:pdf-page="2" src=" doc2.pdf"/>

                </fo:block>

                <fo:block line-height="0pt">

                    <fo:external-graphic rx:pdf-page="3" src=" doc2.pdf"/>

                </fo:block>

                <fo:block line-height="0pt">

                    <fo:external-graphic rx:pdf-page="4" src=" doc2.pdf"/>

                </fo:block>

                <fo:block line-height="0pt">

                    <fo:external-graphic rx:pdf-page="5" src=" doc2.pdf"/>

                </fo:block>

</fo:flow>

</fo:page-sequence>

 

The other way to do it is to manipulate the intermediate format and insert the <xep:insert-document> right into the structure at the point in which you want it. But this method would not keep track of pages if you needed accurate page numbers on subsequent pages.

 

Kevin

 

From: Charles Porter [mailto:charles.b.porter at rrd.com <mailto:charles.b.porter at rrd.com> ] 
Sent: Wednesday, July 22, 2015 6:55 AM
To: Kevin Brown <kevin at renderx.com <mailto:kevin at renderx.com> >
Cc: RenderX Community Support List <xep-support at renderx.com <mailto:xep-support at renderx.com> >
Subject: Re: [xep-support] inserting pdf documents, OK, a new CoolTool

 

Kevin:

 

I've reviewed the files, and this doesn't quite meet our needs.  Thank you very much, though, for the response.

 

Thanks again,




________________________________________________________________________

Charles B. Porter | Technical Analyst, Customer Facing Systems | RR Donnelley

655 Brighton Beach Rd | Menasha, WI 54952
Office: 920.751.7612 | Mobile: 920.450.3480 | Fax: 920.751.7686
charles.b.porter at rrd.com <mailto:charles.b.porter at rrd.com> 
http://www.rrdonnelley.com <http://rrdonnelley.com> 

 

On Tue, Jul 21, 2015 at 1:10 PM, Kevin Brown <kevin at renderx.com <mailto:kevin at renderx.com> > wrote:

Charles:

 

I was going to post this soon anyway but you could examine this and perhaps this would work for you.

Packaged up with a soon to be released Cloudformatter client is a sample XSL called “Merge and Stamp”.

Essentially, it uses the extension attribute rx:pdf-page to insert an fo:external-graphic which is a specific page of a whole PDF.

If you know the number of pages, you can just use a template to iterate over the document and insert a “page” for each page.

The stylesheet also has various methods of marking each page in the package.

 

Contact me directly for any help you need in modifying this for your needs.

 

Given an XML input like this one:

 

<package xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <documents>
   <document pages="1" src="cover.pdf">
      <bookmark>Cover</bookmark>
    </document>
    <document pages="5" src="hammer.pdf">
      <bookmark>My Document</bookmark>
    </document>
  </documents>
  <watermark>
    <mark rotate="-45" 
      fill="yellow" 
      font-family="Helvetica" 
      font-size="80pt" 
      stroke="silver"
      fill-opacity="0.3">DRAFT</mark>
  </watermark>
</package>

 

The stylesheet below would:

 

1)      Iterate over each <document>

2)      Create <fo:external-graphic> elements for each page in the packages

3)      It also puts bookmarks down for each of the packages

4)      It also stamps each page (in the case above with a drawn in SVG watermark at 45 degrees that says “DRAFT”)

 

You could adopt something similar to process the two documents you have and put them into your document.

Or, you could just see what this does and just do the same in your document.

Meaning, instead of using rx:insert-document, use rx:pdf-page for each of the pages. Like this (taking five pages from the hammer document in order and inserting them into a flow):

<fo:block-container id="d0e11">
                <fo:block line-height="0pt">
                    <fo:external-graphic rx:pdf-page="1" src="hammer.pdf"/>
                </fo:block>
                <fo:block line-height="0pt">
                    <fo:external-graphic rx:pdf-page="2" src="hammer.pdf"/>
                </fo:block>
                <fo:block line-height="0pt">
                    <fo:external-graphic rx:pdf-page="3" src="hammer.pdf"/>
                </fo:block>
                <fo:block line-height="0pt">
                    <fo:external-graphic rx:pdf-page="4" src="hammer.pdf"/>
                </fo:block>
                <fo:block line-height="0pt">
                    <fo:external-graphic rx:pdf-page="5" src="hammer.pdf"/>
                </fo:block>
            </fo:block-container>

 

************

 

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:fo="http://www.w3.org/1999/XSL/Format"
    xmlns:rx="http://www.renderx.com/XSL/Extensions"
    xmlns:svg="http://www.w3.org/2000/svg"
    version="1.0">
  <xsl:variable name="default.page-width" select="'8.5in'"/>
  <xsl:variable name="default.page-height" select="'11in'"/>
  <xsl:template match="/package">
    <fo:root>
      <fo:layout-master-set>
        <xsl:apply-templates select="documents/document" mode="layout"/>
      </fo:layout-master-set>
      <fo:bookmark-tree>
        <xsl:apply-templates select="documents/document" mode="bookmarks"/>
      </fo:bookmark-tree>
      <xsl:apply-templates select="documents/document"/>
    </fo:root>
  </xsl:template>
  <xsl:template name="pglayout">
    <xsl:param name="name"/>
    <fo:simple-page-master master-name="{$name}">
      <xsl:variable name="pw" select="ancestor-or-self::node()/@page-width"/>
      <xsl:attribute name="page-width">
        <xsl:choose>
          <xsl:when test="$pw">
            <xsl:value-of select="$pw[last()]"/>
          </xsl:when>
          <xsl:otherwise>
            <xsl:value-of select="$default.page-width"/>
          </xsl:otherwise>
        </xsl:choose>
      </xsl:attribute>
      <xsl:variable name="ph" select="ancestor-or-self::node()/@page-height"/>
      <xsl:attribute name="page-height">
        <xsl:choose>
          <xsl:when test="$ph">
            <xsl:value-of select="$ph[last()]"/>
          </xsl:when>
          <xsl:otherwise>
            <xsl:value-of select="$default.page-height"/>
          </xsl:otherwise>
        </xsl:choose>
      </xsl:attribute>
      <fo:region-body/>
      <fo:region-after>
        <xsl:attribute name="extent">
          <xsl:choose>
            <xsl:when test="$ph">
              <xsl:value-of select="$ph[last()]"/>
            </xsl:when>
            <xsl:otherwise>
              <xsl:value-of select="$default.page-height"/>
            </xsl:otherwise>
          </xsl:choose>
        </xsl:attribute>
      </fo:region-after>
    </fo:simple-page-master>    
  </xsl:template>
  <xsl:template match="page" mode="layout">
    <xsl:param name="name"/>
    <xsl:variable name="pgnum" select="position()"/>
    <xsl:variable name="docname" select="concat($name,'_pg',$pgnum)"/>
    <xsl:call-template name="pglayout">
      <xsl:with-param name="name" select="$docname"/>
    </xsl:call-template>
  </xsl:template>
  <xsl:template match="document" mode="layout">
    <xsl:variable name="docnum" select="position()"/>
    <xsl:variable name="docname" select="concat('doc',$docnum)"/>
    <xsl:choose>
      <xsl:when test="pages">
          <xsl:apply-templates select="pages/page" mode="layout">
            <xsl:with-param name="name" select="$docname"/>
          </xsl:apply-templates>    
      </xsl:when>
      <xsl:otherwise>
        <xsl:call-template name="pglayout">
          <xsl:with-param name="name" select="$docname"/>
        </xsl:call-template>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>
  <xsl:template match="document" mode="bookmarks">
    <fo:bookmark internal-destination="{generate-id()}">
      <fo:bookmark-title>
        <xsl:value-of select="bookmark"/>
      </fo:bookmark-title>
      <xsl:apply-templates select="pages/page" mode="bookmarks"/>
    </fo:bookmark>
  </xsl:template>
  <xsl:template match="page" mode="bookmarks">
    <fo:bookmark internal-destination="{generate-id()}">
      <fo:bookmark-title>
        <xsl:value-of select="bookmark"/>
      </fo:bookmark-title>
    </fo:bookmark>
  </xsl:template>
  <xsl:template match="watermark">
    <xsl:apply-templates/>
  </xsl:template>
  <xsl:template match="image">
    <fo:block-container position="absolute" top="{@top}" left="{@left}">
      <fo:block>
        <fo:external-graphic content-type="{@mimetype}">
          <xsl:if test="@scale">
            <xsl:attribute name="content-width">
              <xsl:value-of select="@scale"/>
            </xsl:attribute>
          </xsl:if>
          <xsl:attribute name="src">
            <xsl:choose>
              <xsl:when test="@src">
               <xsl:value-of select="@src"/>
              </xsl:when>
              <xsl:otherwise>
                <xsl:text>data:</xsl:text>
                <xsl:value-of select="@mimetype"/>
                <xsl:text>;base64, </xsl:text>
                <xsl:value-of select="."/>
              </xsl:otherwise>
            </xsl:choose>
          </xsl:attribute>
        </fo:external-graphic>
      </fo:block>
    </fo:block-container>
  </xsl:template>
  <xsl:template match="stamp">
    <fo:block-container position="absolute" top="{@top}" left="{@left}">
      <xsl:apply-templates/>
    </fo:block-container>
  </xsl:template>
  <xsl:template match="text">
    <fo:block>
      <xsl:copy-of select="@*"/>
      <xsl:value-of select="."/>
    </fo:block>
  </xsl:template>
  <xsl:template match="mark">
    <fo:block-container position="absolute" top="0" left="0">
      <fo:block>
        <fo:instream-foreign-object>
          <svg width="612pt" height="792pt" xmlns="http://www.w3.org/2000/svg" version="1.1" fill-opacity="0">
            <text transform="translate(306pt, 396pt) rotate({@rotate})"
                text-anchor="middle"
                text-align="center"
                fill="{@fill}"
                font-family="{@font-family}"
                font-size="{@font-size}"
                stroke="{@stroke}"
                fill-opacity="{@fill-opacity}">
              <xsl:value-of select="."/>
            </text>
          </svg>
        </fo:instream-foreign-object>
      </fo:block>
    </fo:block-container>
  </xsl:template>
  <xsl:template match="document">
    <xsl:variable name="docnum" select="position()"/>
    <xsl:variable name="docname" select="concat('doc',$docnum)"/>
    <xsl:variable name="src" select="@src"/>
    <xsl:choose>
      <xsl:when test="pages">
          <xsl:for-each select="pages/page">
            <xsl:variable name="pgnum" select="position()"/>
            <xsl:variable name="mref" select="concat($docname,'_pg',$pgnum)"/>
            <fo:page-sequence master-reference="{$mref}">
              <fo:static-content flow-name="xsl-region-after">
                <xsl:apply-templates select="//watermark"/>
              </fo:static-content>
              <fo:flow flow-name="xsl-region-body">
                <fo:block-container id="{generate-id()}">
                  <xsl:call-template name="genpage">
                    <xsl:with-param name="curpage" select="$pgnum"/>
                    <xsl:with-param name="pages" select="$pgnum"/>
                    <xsl:with-param name="src" select="$src"/>
                  </xsl:call-template>
                </fo:block-container>
              </fo:flow>
            </fo:page-sequence>
          </xsl:for-each>
      </xsl:when>
      <xsl:otherwise>
        <fo:page-sequence master-reference="{$docname}">
          <fo:static-content flow-name="xsl-region-after">
            <xsl:apply-templates select="//watermark"/>
          </fo:static-content>
          <fo:flow flow-name="xsl-region-body">
            <fo:block-container id="{generate-id()}">
              <xsl:call-template name="gendoc">
                <xsl:with-param name="pages" select="@pages"/>
                <xsl:with-param name="src" select="$src"/>
              </xsl:call-template>
            </fo:block-container>
          </fo:flow>
        </fo:page-sequence>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>
  <xsl:template name="gendoc">
    <xsl:param name="pages"/>
    <xsl:param name="src"/>
    <xsl:call-template name="genpage">
      <xsl:with-param name="curpage" select="1"/>
      <xsl:with-param name="pages" select="$pages"/>
      <xsl:with-param name="src" select="$src"/>
    </xsl:call-template>
  </xsl:template>
  <xsl:template name="genpage">
    <xsl:param name="pages"/>
    <xsl:param name="curpage"/>
    <xsl:param name="src"/>
    <xsl:if test="$curpage < ($pages + 1)">
      <fo:block line-height="0pt">
        <fo:external-graphic rx:pdf-page="{$curpage}">          
          <xsl:attribute name="src">
            <xsl:choose>
              <xsl:when test="$src">
                <xsl:value-of select="$src"/>
              </xsl:when>
              <xsl:otherwise>
                <xsl:text>data:application/pdf;base64, </xsl:text>
                <xsl:value-of select="content"/>
              </xsl:otherwise>
            </xsl:choose>
          </xsl:attribute>
        </fo:external-graphic>
      </fo:block>
      <xsl:call-template name="genpage">
        <xsl:with-param name="curpage" select="$curpage + 1"/>
        <xsl:with-param name="pages" select="$pages"/>
        <xsl:with-param name="src" select="$src"/>
      </xsl:call-template>
    </xsl:if>
  </xsl:template>
</xsl:stylesheet>

 

 

 

 

From: Xep-support [mailto:xep-support-bounces at renderx.com <mailto:xep-support-bounces at renderx.com> ] On Behalf Of Charles Porter
Sent: Tuesday, July 21, 2015 9:32 AM
To: xep-support at renderx.com <mailto:xep-support at renderx.com> 
Subject: [xep-support] inserting pdf documents

 

Hello,

 

I'm exploring ways to insert up to two pdf documents in a row before a specific flow in the document.  Using @rx:insert-document works great for inserting a single document.  The only way I've found to insert two documents in a row, is to create a empty fo:page-sequence and set @rx:insert-document on that.

 

So if I want to insert two documents before the page-sequence using master-reference="seq1",

I create the page-sequence with master-reference="ins1" and rx:insert-document (no content in the flow), then create page-sequence with master-reference="seq1" and rx-insert-document.  

 

<fo:page-sequence master-reference="ins1" rx:insert-document="url(some_url)">

    <fo:flow flow-name="xsl-region-body"><fo:block/></fo:flow>

</fo:page-sequence>

<fo:page-sequence master-reference="seq1" rx:insert-document="url(some_other_url)">

    <fo:static-content flow-name="xsl-region-before">

    ...

 

If I do it this way, I wind up with a blank page between the first inserted document and the second inserted document.  Is there a way that I can do this and not have the blank page between the two?

 

Thanks in advance.


________________________________________________________________________

Charles B. Porter | Technical Analyst, Customer Facing Systems | RR Donnelley

655 Brighton Beach Rd | Menasha, WI 54952
Office: 920.751.7612 | Mobile: 920.450.3480 | Fax: 920.751.7686
charles.b.porter at rrd.com <mailto:charles.b.porter at rrd.com> 
http://www.rrdonnelley.com <http://rrdonnelley.com> 

 

 

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.renderx.com/pipermail/xep-support/attachments/20150722/13b537ba/attachment-0001.html>


More information about the Xep-support mailing list