user5249203 user5249203 - 17 days ago 3
PHP Question

In Multicell table how to draw border according to number of lines in each row and prevent data flowing into new page

I am creating a pdf table using Multicell() function in PHP/TCPDF. Two issues I face are


  1. Each row of the table (3x3) has varying number of data lines, so how to draw horizontal line for each row considering the max lines of respective row.

  2. How to account for a page break ? For instance, if row 2 data flows into the next page. How to re-write the complete table in new page, or start row 2 in new page with sub-headings of the table ?
    Any inputs on these 2 scenarios is appreciated.
    I tried the following with inputs from this article http://www.onemoretake.com/2009/03/27/revisited-tcpdf-variable-height-table-rows-with-multicell/

    public function xyz($arr_1){
    $f1 = $arr_1[f1];
    $f2 = $arr_1[f2];
    $f3 = $arr_1[f3];
    $numL1 = substr_count($f1, "\n" );
    $numL2 = substr_count($f2, "\n" );
    $numL3 = substr_count($f3, "\n" );
    $Maxrowlines = max($numL1, $numL2, $numL3)*6;
    if($this->GetY() + $Maxrowlines > $this->PageBreakTrigger){
    $this->AddPage();
    }
    $startx = $this->GetX();
    $starty = $this->GetY();
    $rowmaxy = $starty + $Maxrowlines;
    $this->MultiCell(40,10,$txt = $arr_1[f1],'0','L',0, $ln =0);
    $this->MultiCell(40,10,$txt = $arr_2[f2],'0','L',0, $ln =0);
    $this->MultiCell(40,10,$txt = $arr_3[f3],'0','L',0, $ln =0);
    $this ->SetXY($startx, $starty);
    $tempy = $this->GetY();
    $this->SetXY($startx, $tempy);
    if($temp < $rowmaxy){
    $diffy = $rowmaxy - $tempy;
    $this->MultiCell(40,$diffy, '' , '0', 'C', 0);
    } else {
    $this->MultiCell(40,0,'','0','C',0);
    }
    $addx = $this->GetX();
    $startx+= $addx;
    }
    $arr_1 = array(f1=> $apple , f2=> $oranges, f3=> $mangoes);
    $pdf->xyz($arr_1);


Answer

Well the fix was easy. Took some time though, here is the fix.

# define methods and classes-----------------
# constructors....class...
public function xyz($arr_1){
     $f1 = $arr_1[f1];
     $f2 = $arr_1[f2];
     $f3 = $arr_1[f3];
    $numL1 = substr_count($f1, "\n" );
    $numL2 = substr_count($f2, "\n" );
    $numL3 = substr_count($f3, "\n" );
    $Maxrowlines = max($numL1, $numL2, $numL3)*6;

      $startx = $this->GetX();
      $starty = $this->GetY();
      $rowmaxy = $starty + $Maxrowlines;
$this ->SetXY($startx, $starty);
      $this->MultiCell(40,10,$txt = $arr_1[f1],'0','L',0, $ln =0);
      $this->MultiCell(40,10,$txt = $arr_2[f2],'0','L',0, $ln =0);
      $this->MultiCell(40,10,$txt = $arr_3[f3],'0','L',0, $ln =0);
    # Now, if the lines in a multicell are overflowing into next row
    # get current Y position store it in a variable
    # SetXY to the current Y and if the tempy is less than the rowmaxy we..
    # calculate extend cell height with that difference 

        $tempy = $this->GetY();
            $this->SetXY($startx, $tempy);
            if($tempy < $rowmaxy){
            $diffy = $rowmaxy - $tempy;
            $this->MultiCell(40,$diffy, '' , '0', 'C', 0);
            } 
  }
#--------------Call the functions.........
#..... invoke the main class and methods...
# main code as follows..
$arr_1 = array(f1=> $apple , f2=> $oranges, f3=> $mangoes);
$rowcount = max($pdf->getNumLines($arr_1 ['f1'],40),
                                $pdf->getNumLines($arr_1['f2'],40),
                                $pdf->getNumLines($arr_1 ['f3'],40));
$height_of_cell = $pdf->GetY()+($rowcount*6); # 6 is adjustment of the
# height to font you use. My case, `helvetica`
$dimensions = $pdf->getPageDimensions();
$page_height = $dimensions['hk'];# standard value 286;
$bottom_margin = $dimensions['bm'];# standard value of 20
if($height_of_cell > $page_height - $bottom_margin) {   
    $pdf->AddPage();
    $pdf->your_TableHeader();# call table header if there is one
    $pdf->Ln(10); # No. Line you want to start printing data below header 
}
$pdf->xyz($arr_1); 

Update, Looks like this answer does not address overflow of all the rows it is specific to 1 row. Any suggestion or improvements are accepted.On the other note, the page break works perfect.