Generating PDF DocumentsProblemYou have an application that generates a report, a receipt, or some other output that you'd like users to be able to save. You'd like to generate this output as PDF documents for consistent formatting and convenient distribution. SolutionUse Ruby FPDF to create PDF documents from within your Rails application. First, download Ruby FPDF from http://brian.imxcc.com/fpdf/rfpdf153c.tar.gz. Extract the archive, and move the file called fpdf.rb to the your application's lib directory for it to be available to your controllers. Next, create a Reports Controller that calls require to include the PDF creation library in your lib directory. This controller defines a private method called pdf_report_card and a public method or action called pdf_report. app/controllers/reports_controller.rb: class ReportsController < ApplicationController require 'fpdf' def index end def pdf_report # Data col_sizes = [40,20,20,20] data = [['Course','Exam 1','Exam 2','Final'], ['ENGLISH 101','90','87','B'], ['MUSIC 5A','97','100','A'], ['CALC 2','98','91','A'], ['SWIM','89','84','B'], ['HIST 110','91','81','B']] send_data pdf_report_card(col_sizes, data), :filename => "report.pdf", :type => "application/pdf" end private def pdf_report_card(col_sizes, data) pdf = FPDF.new pdf.AddPage pdf.SetFont('Arial','B') pdf.SetFontSize(10) pdf.SetFillColor(50,50,50) pdf.SetTextColor(255) pdf.SetDrawColor(0) pdf.SetLineWidth(0.2) # Table Header i = 0 col_sizes.each do pdf.Cell(col_sizes[i],7,data[0][i],1,0,'C',1) i += 1 end pdf.Ln() pdf.SetFillColor(218,206,255) pdf.SetTextColor(0) pdf.SetFont('Arial') fill = 0 # Table Data data[1..-1].each do |row| pdf.Cell(col_sizes[0],6,row[0],'LR',0,'L',fill) pdf.Cell(col_sizes[1],6,row[1],'LR',0,'L',fill) pdf.Cell(col_sizes[2],6,row[2],'LR',0,'L',fill) pdf.Cell(col_sizes[3],6,row[3],'LR',0,'C',fill) pdf.Ln() fill = (fill-1).abs % 2 end # Bottom Table Border total = 0 col_sizes.each {|x| total += x} pdf.Cell(total,0,'','T'); pdf.Output end end The index.rhtml simply creates a link that generates a PDF report card: app/views/reports/index.rhtml: <h1>Report</h1> <%= link_to 'Make PDF', :action => 'pdf_report' %> DiscussionThe solution displays a 'Make PDF' link. Clicking this link calls the pdf_report action of the Reports Controller when clicked. pdf_report defines an array of four integers that are the column widths of the table to be generated. The actual data to be output is defined as a two-dimensional array and stored in data. The PDF version of the report is returned to the user with the send_data method, which itself calls pdf_report_card to create the PDF. send_data also takes the :filename and :type options, which help browsers render or save the file. pdf_report_card takes two array arguments; the column widths and a structure of the data to be output. The function creates a new FPDF object and then sets up display properties for the table header, including font and background color. The contents of data is then iterated over, and the body of the table is created. The final call to pdf.Cell draws the bottom border to the table. Figure 15-2 shows the solution's PDF output. Figure 15-2. A PDF containing a list of classes with exam scoresSee Also
|