I have a custom object as competitor ,forecast ,std obj as quote and quotelineitem. I have a created a visual force page in a data form ,but it should be in PDF report .So i have added an attribute as "renderas=pdf" ,but the page does not look like a PDF ,it gets messed up completely with rows and columns,it should be linked on the Quote header to open this PDF.Any sugesstion plz. 1) Visual force page as a PDF report 2) linked on the Quote header to open this PDF 3)Forecast object is not linked to quote object ,how should i call those field into the vf page ,using wrapper class i need do that. Here is the Code : using the "render as"

 <!--This is the Quote object section -->

 <apex:pageBlockSection title="General Information">

  <apex:inputField value="{!Quote.Name}" label="Customer Name"/><!-- need to find out as which name field to be used -->
  <apex:inputField value="{!Quote.Effective_Date__c}" label="Accout Type"/><!-- need to find out as which name field to be used -->
  <apex:inputField value="{!Quote.Effective_Date__c}" label="Date"/>
  <apex:inputField value="{!Quote.Effective_Date__c}" label="Expected Order Date" required="true"/>
  <apex:inputField value="{!Quote.Comments__c}" label="Internal Comments"/><!-- need to be created this field on quote object -->
  <apex:inputField value="{!Quote.Comments__c}" label="External Comments"/> 
  <apex:inputField value="{!Quote.Opportunity.Probability}" label="Probability(%)"/>
  <apex:inputField value="{!Quote.Opportunity.AccSegment__c}" label="Segment"/>
  <apex:inputField value="{!Quote.Opportunity.AccApplication__c}" label="Application"/>
  <apex:inputField value="{!Quote.Opportunity.Persona__c}" label="Persona"/>
  <apex:inputField value="{!Quote.Opportunity.Region__c}" label="Geography"/><!--<!-- need to findout this field on opportunity object -->


 <!--This is the QuotelineItem object section -->

 <apex:pageBlockSection title="Quote Line Item Details">

   <apex:pageBlockTable value="{!Quote.Quotelineitems}" var="qli">

     <apex:column headerValue="Part Numbers">
       <apex:inputField value="{!qli.Product2}"/>
     <apex:column headerValue="Price">
       <apex:inputField value="{!qli.UnitPrice}"/>
     <apex:column headerValue="End Customer Price">
       <apex:inputField value="{!qli.End_Customer_Price__c}"/>
     <apex:column headerValue="Quantity">
       <apex:inputField value="{!qli.Quantity}"/>
     <apex:column headerValue="Total">
       <apex:inputField value="{!qli.TotalPrice}"/>



   <!--This is the QuotelineItem object section -->

<apex:pageBlockSection title="Period Name">


    <!--This is the justification and Account section -->

    <apex:inputField value="{!Quote.Account.Name}" label="RFQ Justification:"/> <!--need to find out this field -->
    <apex:inputField value="{!Quote.Account.Main_Customers_of_Account__c}" label="Main Customers of Account:"/> 
    <apex:inputField value="{!Quote.Account.Bridgelux_Competition_at_Account__c}" label="Bridgelux Competition at Account:"/>
    <apex:inputField value="{!Quote.Account.Servicing_Region__c}" label="Geographic regions serviced:"/>
    <apex:inputField value="{!Quote.Account.Annual_LED_Revenue__c}" label="Annual lighting revenue:"/>
    <apex:inputField value="{!Quote.Account.Annual_LED_Revenue__c}" label="Annual LED revenue or percent:"/>
    <apex:inputField value="{!Quote.Account.Annual_Purchases_of_LED_Sources_SAM__c}" label="Annual Purchases of LED Sources (SAM):"/>
    <apex:inputField value="{!Quote.Account.Percent_of_LED_purchases_that_are_COB__c}" label="Percent_of_LED_purchases_that_are_COB__c:"/>
    <apex:inputField value="{!Quote.Account.Percent_of_LED_purchases_that_are_COB__c}" label="Other Info:"/> <!--need to find out this field -->

    <!--This is the Competitive data section -->

<apex:pageBlockTable value="{!Quote.Competitor_s__r}" var="com">

     <apex:column headerValue="Company">
       <apex:inputField value="{!com.Part_Number__c}"/>
     <apex:column headerValue="Product series">
       <apex:inputField value="{!com.Product_Series__c}"/>
     <apex:column headerValue="Part Numbers">
       <apex:inputField value="{!com.Part_Number__c}"/>
     <apex:column headerValue="Price">
       <apex:inputField value="{!com.Price_Offered__c}"/>
     <apex:column headerValue="volume">
       <apex:inputField value="{!com.Volume__c}"/>
     <apex:column headerValue="Date Price is Valid">
       <apex:inputField value="{!com.Date_Price_is_Valid__c}"/>


<apex:pageBlockButtons >

   <apex:commandButton value="EDIT" action="{EDIT}"/>
   <apex:commandButton value="SAVE" action="{SAVE}"/>
   <apex:commandButton value="CANCEL" action="{CANCEL}"/>

  • @KeithC:Thanks for your reply.Point 2) On Quote object , a link should be displayed at the header.So once the user clicks the link , it should open the PDF report.Point3)we have a managed packaged installed as opportunity forcecast .This (opportunity forecast obj) is not linked to the Quote object ,but i need to call those fields in vf page .how can i do that ,is it thru wrapper class or i need to build a relation ship and call them. – nikkey Nov 26 '14 at 11:58
  • @KeithC:how to get static resouce file. – nikkey Nov 26 '14 at 12:01

This answer mainly addresses your item 1).

Cleanly formatted PDF output is best achieved by using mainly raw HTML tags with simple CSS styling. See Best Practices for Rendering PDFs for the apex tags that are safe to use. While developing, it is helpful to set renderAs="HTML" so you can use your browser's CSS tools to get the styling right and then switch to renderAs="PDF" late in the process.

Here is an example of a PDF page:

<apex:page standardController="Claim__c" extensions="ClaimContentController"
        applyHtmlTag="false" renderAs="PDF">

        <link href="{! $Resource.PdfCss }" rel="stylesheet" type="text/css"/>

    <div class="title">Claim Attachments {!claim.Name}</div>

    <h1>Claim Summary</h1>
    <table class="detailList" border="0" cellpadding="0" cellspacing="0">
            <td class="labelCol">Claim</td>
            <td class="data2Col"><apex:outputField value="{!claim.Name}"/></td>
            <td class="labelCol">Policy</td>
            <td class="data2Col"><apex:outputField value="{!claim.Policy__r.Name}"/></td>
            <td class="labelCol">Benefit Type</td>
            <td class="data2Col">{!claim.BenefitType__c}</td>
            <td class="labelCol">Claimant/Insured</td>
            <td class="data2Col">{!claimantInsuredName}</td>
            <td class="labelCol">Claim Owner</td>
            <td class="data2Col"><apex:outputField value="{!claim.OwnerId}"/></td>
    <p>This document was created {!formattedNow}.</p>

    <table class="bordered">
                <th class="bordered">Related To</th>
                <th class="bordered">Type</th>
                <th class="bordered">Name</th>
                <th class="bordered">Description</th>
                <th class="bordered">Created By</th>
            <apex:repeat value="{!attachments}" var="a">
                <td class="bordered"><apex:outputText value="{!a.ParentName}"/></td>
                <td class="bordered"><apex:outputText value="{!a.parentType}"/></td>
                <td class="bordered"><apex:outputField value="{!a.sob.Name}"/></td>
                <td class="bordered"><apex:outputField value="{!a.sob.Description}"/></td>
                <td class="bordered"><apex:outputField value="{!a.sob.CreatedById}"/></td>


You may need to create a normal Visualforce page to make any selections of data that is to be presented in the PDF and then pass those values to the PDF page as parameters so that the PDF page's controller can query the right data. I'm not entirely clear what you are asking in your item 2) and 3).

  • :can u help me out with the Apex class for the given example – nikkey Nov 26 '14 at 16:11
  • @nikkey My class had (simplifying a bit) a single object queried and made available in a single public Claim__c claim {get; set;} property plus a list of objects available in an array in a list property public List<Attachment> attachments {get; set;} so that one needed to use the repeat and have the values presented in table rows. But it looks like you already have a controller so I suggest you work on swapping out the apex tags for the raw HTML equivalents. – Keith C Nov 26 '14 at 16:56

Per Best Practices for Rendering PDFs, <apex: inputField> is one of the Components That Are Unsafe to Use in a PDF. You'll want to avoid using <apexPageBlock> and <apex: pageTable> for the same reasons. Similarly, no active content is safe. such as the <apex: commandButton> code you're using. Follow @KeithC's advice by using regular HTML tables to hold your data.

Pulling the other items in is usually best done via a custom controller that queries the data you need and puts it in a wrapper class. You then pass it to your page and use repeats to output it on the page.

You can create links from VF preview pages or have buttons that "print to PDF", but you can't link from a PDF. So you may want to create multiple buttons from the page that you generate these pages from. That's what we've done for clients in the past. There's a freebie unmanaged package on the App exchange called "Simple Quotes and Invoices" that you may want to install which might be helpful towards creating your code for this.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.