getting "TCPDF ERROR: Some data has already been output, can't send PDF file"

Help
2014-04-05
2014-04-16
  • Wayne Sewell
    Wayne Sewell
    2014-04-05

    I am not sure where I am writing to the output stream before calling $pdf->Output.
    I did have a print statement for the HTML, but that was commented out.
    I basically took the example and replaced the canned table with my own.

    Here is the redone example:

    <?php
    //============================================================+
    // File name   : example_048.php
    // Begin       : 2009-03-20
    // Last Update : 2013-05-14
    //
    // Description : Example 048 for TCPDF class
    //               HTML tables and table headers
    //
    // Author: Nicola Asuni
    //
    // (c) Copyright:
    //               Nicola Asuni
    //               Tecnick.com LTD
    //               www.tecnick.com
    //               info@tecnick.com
    //============================================================+
    
    /**
     * Creates an example PDF TEST document using TCPDF
     * @package com.tecnick.tcpdf
     * @abstract TCPDF - Example: HTML tables and table headers
     * @author Nicola Asuni
     * @since 2009-03-20
     */
    
    // Include the main TCPDF library (search for installation path).
    require_once('tcpdf_include.php');
    
        $field_lengths[] = "50"; 
        $field_lengths[] = "200";
        $field_lengths[] = "40";
        $field_lengths[] = "40";
        $field_lengths[] = "40";
        $field_lengths[] = "40";
        $field_lengths[] = "40";
        $field_lengths[] = "200";
    
        $field_names[] = "Date";
        $field_names[] = "Job Name";
        $field_names[] = "Client Code";
        $field_names[] = "Client PO Number";
        $field_names[] = "Your PO Number";
        $field_names[] = "Job Number";
        $field_names[] = "Amount";
        $field_names[] = "Remarks";
    
        $field_orientations[] = "center";
        $field_orientations[] = "left";
        $field_orientations[] = "center";
        $field_orientations[] = "center";
        $field_orientations[] = "center";
        $field_orientations[] = "center";
        $field_orientations[] = "right";
        $field_orientations[] = "left";
    
        function generate_field($width, $align, $val)
    
        {
            return '<td align="' . $align . '" width="' . $width . '">' . $val . '</td>';
        }
    
        function generate_row($invals, $field_orientations, $field_lengths, $header=0, $style='')
    
        {
    
            if ($style != '') $html = '<tr style="' . $style . '">';
            else $html = '<tr>';
            $field_orientation = "center";
            $index = 0;
            $vals = $invals;
            foreach ($vals as $val) {
                if (!$header) $field_orientation = $field_orientations[$index];
                $length = $field_lengths[$index];
                $html .= generate_field($length, $field_orientation, $val);
                $index++;
            }
    
            $html .= '</tr>';
    
            return $html;
    
        }
    
    // create new PDF document
    $pdf = new TCPDF(PDF_PAGE_ORIENTATION, PDF_UNIT, PDF_PAGE_FORMAT, true, 'UTF-8', false);
    
    // set document information
    $pdf->SetCreator(PDF_CREATOR);
    $pdf->SetAuthor('Nicola Asuni');
    $pdf->SetTitle('TCPDF Example 048');
    $pdf->SetSubject('TCPDF Tutorial');
    $pdf->SetKeywords('TCPDF, PDF, example, test, guide');
    
    // set default header data
    $pdf->SetHeaderData(PDF_HEADER_LOGO, PDF_HEADER_LOGO_WIDTH, PDF_HEADER_TITLE.' 048', PDF_HEADER_STRING);
    
    // set header and footer fonts
    $pdf->setHeaderFont(Array(PDF_FONT_NAME_MAIN, '', PDF_FONT_SIZE_MAIN));
    $pdf->setFooterFont(Array(PDF_FONT_NAME_DATA, '', PDF_FONT_SIZE_DATA));
    
    // set default monospaced font
    $pdf->SetDefaultMonospacedFont(PDF_FONT_MONOSPACED);
    
    // set margins
    $pdf->SetMargins(PDF_MARGIN_LEFT, PDF_MARGIN_TOP, PDF_MARGIN_RIGHT);
    $pdf->SetHeaderMargin(PDF_MARGIN_HEADER);
    $pdf->SetFooterMargin(PDF_MARGIN_FOOTER);
    
    // set auto page breaks
    $pdf->SetAutoPageBreak(TRUE, PDF_MARGIN_BOTTOM);
    
    // set image scale factor
    $pdf->setImageScale(PDF_IMAGE_SCALE_RATIO);
    
    // set some language-dependent strings (optional)
    if (@file_exists(dirname(__FILE__).'/lang/eng.php')) {
        require_once(dirname(__FILE__).'/lang/eng.php');
        $pdf->setLanguageArray($l);
    }
    
    // ---------------------------------------------------------
    
    // set font
    $pdf->SetFont('helvetica', 'B', 20);
    
    // add a page
    $pdf->AddPage();
    
    $pdf->Write(0, 'Invoice for Joe Blow of Insane Clown Posse', '', 0, 'L', true, 0, false, false, 0);
    
    $pdf->SetFont('helvetica', '', 8);
    
    // -----------------------------------------------------------------------------
    
    // Table with rowspans and THEAD
        $tbl = '<table border="1" cellpadding="2" cellspacing="2">';
        $tbl .= '<thead>';
        $tbl .= generate_row($field_names,"", $field_lengths,1,"background-color:#FFFF00;color:#0000FF;");
        $tbl .= '</tr></thead>';
        $tbl .= generate_row(explode("~","Mar 1, 2013~My Terrific Job~K47~4405~20131~1105~12.34~request 104294501, minimum charge per job of $23.00"), $field_orientations, $field_lengths);
    
        $tbl .= generate_row(explode("~","Mar 1, 2013~Buncha Junk~J53~606606~48132~34567~106.50~request 104294501, minimum charge per job of $23.00"), $field_orientations, $field_lengths);
    
     $tbl .= generate_row(explode("~","Mar 1, 2013~Insane Document~LLX035~48440~30378~222~11.50~request 104294501, minimum charge per job of $23.00"), $field_orientations, $field_lengths);
    
     $tbl .= generate_row(explode("~","Mar 1, 2013~My Manifesto~KNJ222~414~8075~73009~50.25~request 104294501, minimum charge per job of $23.00"), $field_orientations, $field_lengths);
    
     $tbl .= generate_row(explode("~","Mar 1, 2013~I dont believe it~1105~23101~87601~93340~232.32~request 104294501, minimum charge per job of $23.00"), $field_orientations, $field_lengths);
    
     $tbl .= generate_row(explode("~","Mar 1, 2013~What, Me Worry?~KRX455~959~91730~50857~41.41~request 104294501, minimum charge per job of $23.00"), $field_orientations, $field_lengths);
    
        $tbl .= '</table>';
    //print($tbl);
    //exit(0);
    
    $pdf->writeHTML($tbl, true, false, false, false, '');
    
    $pdf->writeHTML($tbl, true, false, false, false, '');
    
    $pdf->writeHTML($tbl, true, false, false, false, '');
    
    $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
        $pdf->writeHTML($tbl, true, false, false, false, '');
    
    // -----------------------------------------------------------------------------
    
    //Close and output PDF document
    $pdf->Output('example_048_honk.pdf', 'I');
    
    //============================================================+
    // END OF FILE
    //============================================================+
    

    At this point I haven't changed that much from the original example.
    I am just trying to get my format settled before
    continuing on with generating real data. I apologize for the weird indentation, due to
    rebellious language-sensitive editor. Rather than having you figure out the actual HTML
    generated by the PHP functions, here it is:

    <table border="1" cellpadding="2" cellspacing="2">
        <thead>
          <tr style="background-color:#FFFF00;color:#0000FF;">
            <td align="center" width="50">Date</td>
    
            <td align="center" width="200">Job Name</td>
    
            <td align="center" width="40">Client Code</td>
    
            <td align="center" width="40">Client PO Number</td>
    
            <td align="center" width="40">Your PO Number</td>
    
            <td align="center" width="40">Job Number</td>
    
            <td align="center" width="40">Amount</td>
    
            <td align="center" width="200">Remarks</td>
          </tr>
        </thead>
    
        <tr>
          <td align="center" width="50">Mar 1, 2013</td>
    
          <td align="left" width="200">My Terrific Job</td>
    
          <td align="center" width="40">K47</td>
    
          <td align="center" width="40">4405</td>
    
          <td align="center" width="40">20131</td>
    
          <td align="center" width="40">1105</td>
    
          <td align="right" width="40">12.34</td>
    
          <td align="left" width="200">request 104294501, minimum charge per job of
          $23.00</td>
        </tr>
    
        <tr>
          <td align="center" width="50">Mar 1, 2013</td>
    
          <td align="left" width="200">Buncha Junk</td>
    
          <td align="center" width="40">J53</td>
    
          <td align="center" width="40">606606</td>
    
          <td align="center" width="40">48132</td>
    
          <td align="center" width="40">34567</td>
    
          <td align="right" width="40">106.50</td>
    
          <td align="left" width="200">request 104294501, minimum charge per job of
          $23.00</td>
        </tr>
    
        <tr>
          <td align="center" width="50">Mar 1, 2013</td>
    
          <td align="left" width="200">Insane Document</td>
    
          <td align="center" width="40">LLX035</td>
    
          <td align="center" width="40">48440</td>
    
          <td align="center" width="40">30378</td>
    
          <td align="center" width="40">222</td>
    
          <td align="right" width="40">11.50</td>
    
          <td align="left" width="200">request 104294501, minimum charge per job of
          $23.00</td>
        </tr>
    
        <tr>
          <td align="center" width="50">Mar 1, 2013</td>
    
          <td align="left" width="200">My Manifesto</td>
    
          <td align="center" width="40">KNJ222</td>
    
          <td align="center" width="40">414</td>
    
          <td align="center" width="40">8075</td>
    
          <td align="center" width="40">73009</td>
    
          <td align="right" width="40">50.25</td>
    
          <td align="left" width="200">request 104294501, minimum charge per job of
          $23.00</td>
        </tr>
    
        <tr>
          <td align="center" width="50">Mar 1, 2013</td>
    
          <td align="left" width="200">I dont believe it</td>
    
          <td align="center" width="40">1105</td>
    
          <td align="center" width="40">23101</td>
    
          <td align="center" width="40">87601</td>
    
          <td align="center" width="40">93340</td>
    
          <td align="right" width="40">232.32</td>
    
          <td align="left" width="200">request 104294501, minimum charge per job of
          $23.00</td>
        </tr>
    
        <tr>
          <td align="center" width="50">Mar 1, 2013</td>
    
          <td align="left" width="200">What, Me Worry?</td>
    
          <td align="center" width="40">KRX455</td>
    
          <td align="center" width="40">959</td>
    
          <td align="center" width="40">91730</td>
    
          <td align="center" width="40">50857</td>
    
          <td align="right" width="40">41.41</td>
    
          <td align="left" width="200">request 104294501, minimum charge per job of
          $23.00</td>
        </tr>
      </table>
    

    So I'm not sure where it gets the idea that I have output anything.

    As a side note, I am getting a lot of these warnings:

    Warning: array_push() expects parameter 1 to be array, null given in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 16878
    Warning: array_push() expects parameter 1 to be array, null given in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 16878
    Warning: array_push() expects parameter 1 to be array, null given in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 16878
    Warning: array_push() expects parameter 1 to be array, null given in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 16878
    Warning: Invalid argument supplied for foreach() in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 19375
    Warning: Invalid argument supplied for foreach() in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 19407
    Warning: array_push() expects parameter 1 to be array, null given in /Applications/AMPPS/www/tcpdf/tcpdf.php on line 16878

     
  • Wayne Sewell
    Wayne Sewell
    2014-04-15

    Never mind. I found the error. There was an extra that hosed everything. It didn't show up above, because the prettyprinter that formatted the HTML fixed the error without telling me. The original was all one line, so prettyprint.

    It would have been nice for it to TELL me something was wrong with my HTML instead of doing weird things, but okay.

     
  • Wayne Sewell
    Wayne Sewell
    2014-04-15

    The editor ate the HTML code. There was an extra < / T R >

     
  • Wayne Sewell
    Wayne Sewell
    2014-04-16

    In hindsight, it all makes perfect sense. The unbalanced HTML caused all the warning messages about arrays, and those messages were the output that caused the total failure. It was complaining about the output it was generating itself.

    If you ever see warnings like that, check your HTML.

     
  • Lubos Dz
    Lubos Dz
    2014-04-16

    Before sending HTML string to TCPDF you should send it to some pretty formater e.g. tidy - it would fix up invalid markups for you. Example:

    if(extension_loaded('tidy')){
        // http://tidy.sourceforge.net/docs/quickref.html
        $tidy = new tidy();
        $fixedHtml = $tidy->repairString($dirtyHtml, array(
            'output-xhtml' => true,
            'show-body-only' => true,
        ), 'utf8');
    }
    
     
    Last edit: Lubos Dz 2014-04-16
  • Wayne Sewell
    Wayne Sewell
    2014-04-16

    Thanks. That is fine if the HTML is coming from some external source, but if I am generating it, as in this case, I should be generating it correctly. The pretty formatting would be unnecessary overhead due to my own sloppiness. But I will keep that in mind for the former case.