+ Start a Discussion
John De SantiagoJohn De Santiago 

PDF Repeating Header and Footer Support

After a lot of persistence I finally was able to get repeating header and footers when rendering a Visualforce page as a PDF. The key to this is the page2PDF support of CSS3. 

 

Here is the css I came up with:

 

<style type="text/css">

@page {

@top-center {

content: element(header);

}

}

div.header {

padding: 10px;

position: running(header);

}

</style>

 

In the visualforce page I have the header setup as a div with the class name "header" the position running command pulls the content in my div and repeats it at the top of every page. The key for some reason is to put your header and footer divs at the top before you put your content on the page.

 

Here is my page

 

<apex:page renderAs="pdf">

<head>

<style type="text/css" media="print">

@page {

@top-center {

content: element(header);

}

@bottom-left {

  content: element(footer);

}

}

 

div.header {

padding: 10px;

position: running(header);

}

div.footer {

display: block;

padding: 5px;

position: running(footer);

}

 

.pagenumber:before {

content: counter(page);

}

.pagecount:before {

content: counter(pages);

}

</style>

</head>

 

<div class="header">

<div>My Header Text</div>

</div>

 

<div class="footer">

<div>Page <span class="pagenumber"/> of <span class="pagecount"/></div>

</div>

 

<div class="content">

<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vestibulum nec nulla turpis. Suspendisse eget risus sit amet lectus ornare varius. Vestibulum ante ipsum primis in faucibus orci luctus et ultrices posuere cubilia Curae; Aenean nec urna purus, adipiscing accumsan massa. Nullam in justo nulla, sed placerat mauris. In ut nunc eget libero posuere luctus. Donec vulputate sollicitudin ultrices. Nulla facilisi. Mauris in sapien arcu. Phasellus sit amet quam non mi ornare tincidunt ac quis lectus.</p>

</div>

</apex:page>

 

I cut the content text short for the purpose of this post. I am sure it will just take some more playing around.

 

Hope this helps someone avoid some late nights like I spent trying to figure this out. :smileyhappy:

 

 

Message Edited by JohnDS on 03-10-2010 07:34 PM
Best Answer chosen by Admin (Salesforce Developers) 
John De SantiagoJohn De Santiago

You need to play around with the margin-top setting in the @page tag of the css or add one if you have not already. I usually just put a margin-top: 100px and margin-bottom:80px to keep the content from overlapping the heading. You can use smaller sizes but this allows room for an image.

 

I have also created a component for adding header and footer tags along with sample code. You can download the component from my blog at http://thurly.net/02s7

All Answers

gtindugtindu
You deserve a medal of some sort.
magdielhfmagdielhf

 

This solution is just genius, it saved me a lot of time as you said, 
Now I have a use case in which the header and footer should not be seen on the cover page of the PDF document and I'm trying to figure out how to do it using this method, 
Could you post any work around for getting this ?
Thanks in advance. 

 

This solution is just genius, it saved me a lot of time as you said, 


Now I have a use case in which the header and footer should not be seen on the cover page of the PDF document and I'm trying to figure out how to do it using this method, 


Could you post any work around for getting this ?


Thanks in advance. 

Ross JamesRoss James

Has anyone arranged the medal for JohnDS?

 

Working through this I now have a problem that my footer is only 2 lines (or so) high. I have a need for at least 2.5cm but can't figure out how to change this. I have looked at margins for the document (assumed that the margins would dictate the header and footer, or at least interfere with it) but no luck.

 

Does anyone have a suggestion on how to change the height of a header or footer?

magdielhfmagdielhf

Actually you are right about margins, I needed to add a big image to the footer of the page, 

 

I just need to update the @page style, something like this, and include the image in the <div> section of the footer

 

        @page{
          @top-center {                   
             content: element(header);               
          }
          @bottom-right {
             content: element(footer_pagenumber);             
          }
          @bottom-center {
             content: element(footer);
          }           
          margin:2em 1em 6em;
        }
Ross JamesRoss James

**bleep**! I will need to get two medals now...

 

Thanks for the (to me, right now) very important info.

TigerPowerTigerPower

Hey guys,

nice thread! I already learned a lot of this, but I still have a problem. I added style element to place header and footer on every page (pdf), but now my content floats on header image. Then I set padding for my content and got the first page acting okay. Now the only problem is that the second page of my pdf does not work with content (content is displayed on the header sections). Any suggestions? What I'm doing wrong here?

 

div.content{
padding: 215px 10px 50px 10px;
}
John De SantiagoJohn De Santiago

You need to play around with the margin-top setting in the @page tag of the css or add one if you have not already. I usually just put a margin-top: 100px and margin-bottom:80px to keep the content from overlapping the heading. You can use smaller sizes but this allows room for an image.

 

I have also created a component for adding header and footer tags along with sample code. You can download the component from my blog at http://thurly.net/02s7

This was selected as the best answer
TigerPowerTigerPower

Thanks JohnDS! :smileyhappy:

BartCBartC

Very nice thread!  

 

But is there a way you can skip the defined header and footer on the first page?

The first page is a title page in my PDF and I don't need a header and footer there.

 

Thx.

 

 

John De SantiagoJohn De Santiago

In the examples I shared at the end of the link you can create alternate first headers. You could just add an entry in your markup with an empty header and then an entry for the rest of your documents that has content. This should essentially create an empty header on the first page.

 

 

Edwin KEdwin K

Hi All,

 

This is good solution for my case, but I've question, why the space between header & content in the first page is different with page 2, 3, and so on where other pages except page 1 have the same space height. I'm using the code as same as in this forum with different content.. Any suggestions would be great..

 

 

Edwin

John De SantiagoJohn De Santiago

Its a good question and one I haven't been able to correct myself. For some reason the tool that renders the PDF must have some kind of default margin allocated to the first page.

 

I have solved for this by duplicating the header tag and adding or removing margin accordingly to accommodate for it. Not an ideal solution but it seems to work. 

 

Also, many of my forms have a different first page header than the rest of the pages so I end up having to create two header tags anyway.

Edwin KEdwin K

Thanks for the advice.. I'll try your solution for my case..

 

Edwin

AnidevAnidev

It's just perfect.

 

Thanks a ton

NRJNRJ

Very nice information...it really helped me!! :)

There are very few sources available for help in this topic and you surely deserve appreciations!! :)

 

In my case the header was repeating properly on each page but, repeatation of footer was not certain. Some times it was displyed on at the end of the document. Then I moved header and footer contents to the top of the body content and it worked for me!! :)

nextdoornextdoor

Hi guys,

 

Is it possible to count page Number based on <apex:repeat> tag.

 

As far, when I select multiple records from list button, the PDF generated will display the sum of all the pages. Is it possible to reset the page counter or something everytime a record is completed ? 

 
Say example, visual force generates PDF from list button where 2 records are selected and click a custom button then as a result PDF generated with totally 5 pages. With help of apex repeat tag, for the first record generates 3 pages and second record generates next 2 pages in a single file.
 
I need to count a page number in a PDF doc as Page 1 of 3, 2 of 3, 3 of 3 and then again 1 of 2 and 2 of 2.
Is it possible? Any suggestions are highly appreciated.

ISVforce PartnerISVforce Partner

JohnDS,

 

Add one more to the list of medals. If you ever visit Austin, TX, beer is on me. Thanks a lot for posting this.

 

regards

Mitesh

vivekanandanvivekanandan

I have used the same code in thevf page , but the header and footer is not getting repeated at all. Even the page number is not displaying at all. Only the header is visible , that too not repeating..

 

Anybody please help me on this.

Mitesh SuraMitesh Sura
vivekanandan,

Can you paste VF code?
AparnaGopalakrishnan.ax1854AparnaGopalakrishnan.ax1854

Which version of VF page are you using? This solution is not working in version 28 and later.

Mitesh SuraMitesh Sura

Try using "applyHtmlTag="false" in your VF page. It does work in API 28. 

 

<apex:page showHeader="false" controller="pdf" cache="true" renderAs="pdf" applyHtmlTag="false">

 

Jon McDermottJon McDermott
The following approach works for me and gives running headers and footers on each page with an image, text, and page numbers. You can create either portrait or landscape PDF pages. Use a static resource for the overall style sheet; the image for the header is in a second static resource file. I adjust the margin-top, margin-bottom, and padding elements to keep the content DIV from overlapping the header and footer. I don't have a usage case where I need the first page to skip the header/footer. In any event:

I use a style sheet resource CSS file that includes the following information:

@page {
  @top-center {
    content: element(header);
  }
  @bottom-left {
content: element(footer);
  }
margin-top: 130px;
margin-bottom: 80px;
}

Then the VF page includes the pertinent following:

<apex:stylesheet value="{!$Resource.CSS}" />
<HEAD>
<STYLE TYPE="text/css" MEDIA="print">
@page {
    /* choose one of the following for page orientation */
    size: landscape;
    /* size: portrait;   */
}

div.header {
    padding: 10px;
    position: running(header);
    border-bottom: solid 1px;
}

div.footer {
    display: block;
    padding: 10px;
    position: running(footer);
    border-top: solid 1px;
}

.pagenumber:before {
    content: counter(page);
}

.pagecount:before {
    content: counter(pages);
}
</STYLE>
</HEAD>
<BODY>
    <!-- HEADER and FOOTER Information -->
    <DIV CLASS="header">
        <TABLE BORDER="0" STYLE="width: 100%">
            <TBODY>
                <TR>
                    <TD CLASS="col-plain-left"><apex:image id="logo" width="157"
                            height="40"
                            url="{!URLFOR($Resource.flags, 'flags/logo.png' )}" /></TD>
                    <TD CLASS="col-plain-center"></TD>
                    <TD CLASS="col-plain-right"><SPAN STYLE="font-size: 9pt">Confidential</SPAN><BR />
                                                                            Report Date: <apex:outputText Value="{0,date,MMMM dd, yyyy}">
                            <apex:param value="{!TODAY()}" />
                        </apex:outputText></TD>
                </TR>
                <TR>
                    <TD COLSPAN="3" CLASS="col-plain-center"><SPAN
                        STYLE="font-size: 11pt; font-weight: bold; font-variant: small-caps; white-space: nowrap;">AGS
                            PDF Example Header for Opportunity  - {!Opportunity.Name}</SPAN></TD>
                </TR>
            </TBODY>
        </TABLE>
    </DIV>

    <DIV CLASS="footer">
        <TABLE BORDER="0" STYLE="width: 100%" CELLSPACING="0" CELLPADDING="0">
            <TBODY>
                <TR>
                    <TD CLASS="col-plain-left"><SPAN STYLE="font-size: 07pt">Copyright
                            © 2007-<apex:outputText Value="{0, date, yyyy}">
                                <apex:param value="{!TODAY()}" />
                            </apex:outputText> My Company, Inc.
                    </SPAN></TD>
                    <TD CLASS="col-plain-right"><SPAN STYLE="font-size: 07pt">PDFexample
                            20140103</SPAN></TD>
                </TR>
                <TR>
                    <TD CLASS="col-plain-left"><SPAN STYLE="font-size: 07pt">{!Opportunity.Id}</SPAN></TD>
                    <TD CLASS="col-plain-right"><SPAN STYLE="font-size: 07pt">Page
                            <SPAN CLASS="pagenumber" /> of <SPAN CLASS="pagecount" /></SPAN></TD>
                </TR>
            </TBODY>
        </TABLE>
    </DIV>

    <DIV CLASS="content">

        /* put your content here  */

    </DIV>
</BODY>

Somneone who is better than me with CSS could probably make this look a lot more logical. I got this to work through some other forum posts and some trial and error.
BijaySBijayS
Even i am facing the issue on the pdf.

On my second page the header and the content is getting overlapped,for page one it is fine.


Anybody please help me on this.

Thanks in Advance.

Raghavendra Reddy .DRaghavendra Reddy .D
Step 1: create a .css file and paste code  from following link .this code will create a header and footer for your page
@page {

@top-center {

content: element(header);

}

@bottom-left {

    content: element(footer);

}

}

div.header {

padding: 10px;

position: running(header);

}

div.footer {

display: block;

padding: 5px;

position: running(footer);

}



.pagenumber:before {

content: counter(page);

}

.pagecount:before {

content: counter(pages);

}
Step 2: create a static resource .Go to SETUP|APP setup |DEVELOP|Static Resources and create a new static resource namely : “dynaPdf” and import above css file into it.

Step 3:  go to SETUP|APP setup |DEVELOP|COMPONENT and create a new component namely : “dynapdfcomponent” and paste  below code
<apex:component >
<apex:attribute required="true"  type="string" name="type" description="specify header and footer type" />

<apex:stylesheet value="{!$Resource.dynaPdf}"/>
<div class="{!type}" style="background-color:rgb(175,117,161);box-shadow: 10px 10px 5px #888888;margin-bottom:200px">
<apex:componentBody />
</div>    
               
</apex:component>

step 4:  Now create a visualforce page from SETUP|APP setup |DEVELOP|Pages  and create a new page namely : “dynaPdf” and paste below code  :
<apex:page standardStylesheets="false" id="pge" renderAs="pdf">


<c:dynapdfcomponent type="header" >

  <div> <apex:image value="https://ap1.salesforce.com/resource/1406185071000/head" height="100px" width="700px"/> </div>
</c:dynapdfcomponent>

  <c:dynapdfcomponent type="footer">
  <div align="right"><span style="float:left;width:80%;padding:30px 0 0 0;text-align:left;">ragava great person verm vko cvmkogfmckomfkoxdmkodxmko</span> <apex:image value="https://ap1.salesforce.com/resource/1406185821000/foo" height="68px" width="100px" style="float:left;"/> </div>

</c:dynapdfcomponent>

<div class="content">
<p>
<!----------------Your content goes here---------->
</p>

</div>

</apex:page>



Cheers..........
moinuddin saifimoinuddin saifi
<apex:page renderAs="pdf">

    <head>

        <style type="text/css" media="print">

            @page {

                @top-center {

                    content: element(header);

                }

                @bottom-left {

                     content: element(footer);

                }

            }

 

            div.header {

                padding: 10px;

                position: running(header);

            }

            div.footer {

                display: block;

                padding: 5px;

                position: running(footer);

            }

 

            .pagenumber:before {

                content: counter(page);

            }

            .pagecount:before {

                content: counter(pages);

            }

how to get pagenumber value and store in variable
AdamGoesTo11AdamGoesTo11
Ok, I have a weird one. I've been trying to add headers and footers and they just plain don't work. Rather than going to the top and bottom of the page, they just appear inline and don't repeat across the pages.

I couldn't find anything wrong with my code when comparing it to snippets from other people, so on a lark, I created a test VF page and copied the OP's code in and... it also doesn't work in my org.  Is anyone else having problems with getting headers and footers to work today/recently?

User-added image