Search code examples
phppdfpdflib

pdflib add textbox with dynamic height


I'm new to PDFLib and i'm trying to get something work

I got the following situation:

There is a quite clean pdf with two textlines. After these two textlines i want to place a paragraph of text. The thing is, the length of these text is dynamic because it is user input. It could even be more then 1 page of text, all in one paragraph. After this paragraph i want to continue adding textlines like i did before the paragraph. This works for me when the text in the paragraph fits on the first page. If it doesn't, text will flow over and i am not able to add more pages. So my question in this case is: "How to create code that will dynamically add more pages if needed?" I assume that the rest of my code is working and the next textline containing "TEST" is actually placed after the paragraph, but the probleem is that this isn't visible because the text flows of the page...

Here is my code (a small part):

$L_i_pageWidth  = 595;
              $L_i_pageHeight = 842;

              $L_i_pagecount = 0;
              $tf = 0;
              $y = 0;

              $L_s_fontNormal = "fontname=din-bold-webfont embedding fontsize=12 " .
                  "encoding=unicode textformat=utf8";

              $L_s_fontLarge = "fontname=din-bold-webfont embedding fontsize=18 " .
                  "encoding=unicode textformat=utf8";

              $L_s_fontSmall = "fontname=din-bold-webfont embedding fontsize=10 " .
                  "encoding=unicode textformat=utf8";


              try {
                $p = new PDFlib();

                # This means we must check return values of load_font() etc.
                $p->set_parameter("errorpolicy", "return");
                $p->set_parameter("SearchPath", "./assets/pdf/input");

                if ($p->begin_document("", "") == 0) {
                  throw new FrameworkException('Exception ' . get_class($e) . ' - ' . $e->getMessage(), 1001, $e);
                }

                /* Start the template */
                /* Page 1 */
                $p->begin_page_ext($L_i_pageWidth, $L_i_pageHeight, "");
                $L_i_pagecount++;
                $y = $L_i_pageHeight - 150;

                $p->fit_textline("text", 75, $y, $L_s_fontNormal);
                $p->fit_textline('This is a line of text', 220, $y, $L_s_fontNormal);
                $y -= 15;

                $text = 'sdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsf sdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsf sdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsf sdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsfsdsssds sddsdsdsf';
                $tf = $p->create_textflow($text, $L_s_fontNormal);
                if ($tf == 0)
                {
                  throw new FrameworkException('Exception ' . get_class($e) . ' - ' . $e->getMessage(), 1001, $e);
                }
                $result = $p->fit_textflow($tf, 75, $y, ($L_i_pageWidth-75), ($y - 800), 'verticalalign=center');
                // probleem: het loopt van de pagina af
                // combineren twee voorbeelden werkt niet

                $textx = $p->get_value("textx", 0);
                $texty = $p->get_value("texty", 0);

                // font
                $fsize = 12;
                $p->set_parameter("errorpolicy", "return");
                $p->set_parameter("textformat", "utf8");
                $font = $p->load_font("Helvetica-Bold", "unicode", "");

                if ($font == 0)
                print_r("Error: " . $p->get_errmsg());

                $p->setfont($font, $fsize);
                $p->set_text_pos(75, $y);
                $p->show_xy("TEST", 75, $texty -= ($fsize*1.2));

                $p->fit_textline("text", 75, $y, $L_s_fontNormal);
                $p->fit_textline('This is a line of text', 220, $y, $L_s_fontNormal);
                $y -= 15;


                $p->suspend_page("");
                foreach(range(1, $L_i_pagecount) as $pagenumber)
                {
                  $p->resume_page("pagenumber ".$pagenumber);

                  $p->end_page_ext("");
                }


                $p->end_document("");

                return $p->get_buffer();
              }
              catch (PDFlibException $e) {
                echo '<pre>';print_r($e);
                  throw new FrameworkException('Exception ' . get_class($e) . ' - ' . $e->getMessage(), 1001, $e);
              }
              catch (Exception $e) {
                  throw new FrameworkException('Exception ' . get_class($e) . ' - ' . $e->getMessage(), 1001, $e);
              }

If any more information is required, please let me know. Thanks in advance!


Solution

  • a simple sample, which demonstrate how you can a textflow handle which span over more then one instance (page, columns etc.) is available in the PDFlib package as well in the PDFlib cookbook. => starter_textflow.php. http://www.pdflib.com/pdflib-cookbook/text-output/starter-textflow/php-starter-textflow/

    A good sample for your case is the cookbook sample "Continue note after Text" http://www.pdflib.com/pdflib-cookbook/text-output/continue-note-after-text/php-continue-note-after-text/

    The relevant code fragment in your code is

    $result = $p->fit_textflow($tf, 75, $y, ($L_i_pageWidth-75), ($y - 800), 'verticalalign=center');

    you should apply the lower left coordinate and the upper right coordinated of the possible area where the text should be placed. In your case, I guess just the y-position of the upper right position is wrong. At the position when you call the fit_textflow() y=677 and so the y-position is ($y-800) = -123. This value is below the lower border of the page, and the text will flow below. Also, I'm not sure, if the "verticalalign=center" is what you expect to get. When using this, the text is placed in the center of the given fitbox.

    So, for the lower value you should apply some > 0 and for the upper y position apply your calculated $y.

    After this fit_textflow() call, please check the $result. If you get "_stop", you know, the complete content is placed to the fitbox area. If you get "_boxfull" you know, there is some content not placed, and you have to call fit_textflow() once again. Probably on the next page.

    After the text is finished, you can use

    $textendy = $p->info_textflow($tf, "textendy"); to retrieve the end position of the placed text. Afterwards you can use this for further calculations for content below.