Wednesday, October 30, 2013

How to Download charts to PDF formate


It gives many problem to export any html or div to pdf  when it content charts because many  pdf converter library do not support chart container and not able to convert that chart or html div to pdf.

        Here I am going to sort out these problem.
These blog show you how to download Charts like google charts and others, to pdf formate at client side.

Here we use three script or technique:

1. First of all we draw charts at html div as we done in previous blog.
2. Then we convert that chart to Image(canvas) using google api (canvg.js) .
3. Convert whole html page to canvas using html2canvas library.
4.download that canvas (as image) to pdf formate using jspdf librar.

//Import html2canvas and jspdf library to you local folder.

//<Script That help to achieve our goal>

1. //script of charts that you use as google api that we use in previous blog.

//convert chart to Image(canvas) used to invoke canvg(); method

<script type="text/javascript" src="http://canvg.googlecode.com/svn/trunk/canvg.js"></script>

//convert html page to canvas using html2canvas library

<script type="text/javascript" src="../js/html2canvas.js"></script>

//Now export canvas to pdf using jspdf library.

<script type="text/javascript" src="/oltapp/js/FileSaver.js"></script>
<script type="text/javascript" src="/oltapp/js/jspdf.js"></script>
<script type="text/javascript" src="/oltapp/js/jspdf.plugin.addimage.js"></script>

Note: we do not need to import all js of jspdf .

lets take an example to fully understand.

Example code:
 <html>
<head>
<script type="text/javascript" src="http://canvg.googlecode.com/svn/trunk/canvg.js"></script>
<script type="text/javascript" src="http://canvg.googlecode.com/svn/trunk/rgbcolor.js"></script>
<script type="text/javascript" src="http://canvg.googlecode.com/svn/trunk/StackBlur.js"></script>
<script type="text/javascript" src="../js/html2canvas.js"></script>
<script type="text/javascript" src="../js/FileSaver.js"></script>
<script type="text/javascript" src="../js/jspdf.js"></script>
<script type="text/javascript" src="../js/jspdf.plugin.addimage.js"></script> 



<script type="text/javascript">

function export_PDF(chartContainer, imgContainer) {

         //main Div Hide
              var el = document.getElementById( 'chart_Container' );
             el.parentNode.removeChild( el );  

        //Chart to Image

          var doc = chartContainer.ownerDocument;
          var img = doc.createElement('img');
          img.src = getImgData(chartContainer);

          while (imgContainer.firstChild) {
               imgContainer.removeChild(imgContainer.firstChild);
           }

             imgContainer.appendChild(img);

      //Pdf Creation

                   var divElements = document.getElementById('expotPdfDiv).innerHTML;
                                         //Get the HTML of whole page
                                         var oldPage = document.body.innerHTML;

                                         //Reset the page's HTML with div's HTML only
                                         document.body.innerHTML =
                                           "<html><head><title></title></head><body>" +
                                           divElements + "</body>";

//convert whole html page to canvas
 
                             html2canvas(document.body, {
                                     onrendered: function(canvas) {
                                       
  // canvas is the final rendered <canvas> element
                                        
 var myImage = canvas.toDataURL("image/JPEG").slice('data:image/jpeg;base64,'.length);
                                        
 // Convert the data to binary form
                                         myImage = atob(myImage)

//new object of jspdf and save image to pdf.

                                         var doc = new jsPDF();
                                         doc.addImage(myImage, 'JPEG', 0, 0, 200,200);
                                          doc.save('pdfName.pdf');
                                      

                                     }
                                 });


}

function getImgData(chartContainer)
  {


     var chartArea = chartContainer.getElementsByTagName('svg')[0].parentNode;
     var svg = chartArea.innerHTML;
     var doc = chartContainer.ownerDocument;
     var canvas = doc.createElement('canvas');
     canvas.setAttribute('width', chartArea.offsetWidth);
     canvas.setAttribute('height', chartArea.offsetHeight);


     canvas.setAttribute(
         'style',
         'position: absolute; ' +
         'top: ' + (-chartArea.offsetHeight * 2) + 'px;' +
         'left: ' + (-chartArea.offsetWidth * 2) + 'px;');
     doc.body.appendChild(canvas);
     canvg(canvas, svg);

     var imgData = canvas.toDataURL("image/JPEG");
    var data = canvas.toDataURL('image/JPEG').slice('data:image/JPEG;base64,'.length);
             
// Convert the data to binary form
             data = atob(data)


     canvas.parentNode.removeChild(canvas);



     return imgData;
  }

</script>

</head>

<body>
 <div id="expotPdfDiv">
<div id="chart_Container" >
----
---        //Here is script for making chart at chart_Container div.
---

</div>

 <div id="chart_image"></div>  //div where chart image genrate

 <button  Onclick=" export_PDF(document.getElementById('chart_Container'), document.getElementById('chart_image')); " > Download PDF</button>

</div>

</body>

</html>



Monday, October 28, 2013

How to make dynameic graph for website (Using Google API)

There are many open source charts library from which you can easily make dynamic charts for your website .I think it is the easiest way to make dynamic charts through Google API for any beginner .

 These tutorial show you how to make Google API Chart.

Step 1:

 <!--Load the AJAX API-->

    <script type="text/javascript" src="https://www.google.com/jsapi"></script>
    <script type="text/javascript">


Step 2:

 // Load the Visualization API , Here we Load API for PIE Chart
 
 google.load('visualization', '1.0', {'packages':['corechart']});
 
 

Step 3:

 // Set a callback to run when the Google Visualization API is loaded ,
//In Simple manner Call the method which invoke google chart.
 
code:
 
google.setOnLoadCallback(drawChart); 


Step 4:

// Callback that creates and populates a data table, 
// instantiates the pie chart, passes in the data and
// draws it.

function drawChart() {
// Create the data table.
 
 var data = google.visualization.arrayToDataTable([
          ['Task', 'Hours per Day'],
          ['Work',     11],
          ['Eat',      2],
          ['Commute',  2],
          ['Watch TV', 2],
          ['Sleep',    7]
        ]);
 
 
// Set chart options

var options = {'title':'My Daily Activities' ,
                     'width':400,
                     'height':300};
// Instantiate and draw our chart, passing in some options.
var chart = new google.visualization.PieChart(document.getElementById('chart_div'));
      chart.draw(data, options);
    }

</script> //here script is over.



Step 5:

<!--Div that will hold the pie chart-->
 
 <div id="chart_div" style="width:400; height:300"></div>
 

Now you have pie chart on your "chart_div" with static data of  "data" variable just change the data variable according to you dynamic data and you get real pie chart. you can also change charts option according to you .

Creating PDF in spring MVC

Maven Dependency :

Add following dependency in your pom.xml 
        
        <dependency>
            <groupId>com.itextpdf</groupId>
            <artifactId>itextpdf</artifactId>
            <version>5.3.4</version>
        </dependency>


Controller code :

    @RequestMapping(value = "/generatePDF/{empId}",method = RequestMethod.GET)
    private void downloadPDF(@PathVariable Integer empId,
                                    HttpServletResponse response,
                                    HttpServletRequest request, ModelMap model) 
                                    throws IOException {
        
        List<TaskEntry> taskEntryList =  taskEntryService.retrieveAllTask(empId);\
       //here TaskEntry is your Domain of respective class
       //here taskEntryService is your service layer from which you are accessing Data.
       String orignalFileName="sample.pdf";

        try {
            Document document = new Document();
            response.setHeader("Content-Disposition", "outline;filename=\"" +orignalFileName+ "\"");
            PdfWriter.getInstance(document, response.getOutputStream());

            document.open();
            document.add(createFirstTable(taskEntryList ));
            document.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }






public PdfPTable createFirstTable(List<TaskEntry> taskEntryList ) throws ParseException {
        SimpleDateFormat sdf= new SimpleDateFormat("yyyy-MM-dd");
        String fromDate=sdf.format(pdfForm.getFromDate());
        String toDate=sdf.format(pdfForm.getToDate());
        // a table with three columns
        PdfPTable table = new PdfPTable(2);
        // the cell object
        PdfPCell cell;
        // we add a cell with colspan 3
        cell = new PdfPCell(new Phrase("TASK DETAILS"));
        cell.setColspan(2);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase("From"+fromDate+"TO"+toDate));
        cell.setColspan(2);
        table.addCell(cell);
        table.addCell("DATE:");
        table.addCell("TASK:");
        for(TaskEntry taskEntry: taskEntryList)  
       {
           table.addCell(taskEntry.task);
        }
        return table;
    }

For any query Do comment