Text getting clipped when generating PDF using FPDF/FPDI/TCPDF - php

I have a PHP project where I am opening up a premade PDF, and filling it out with data via PHP. The problem I am having is that one of the text elements isn't showing up. I am positioning it towards the bottom right of the PDF page. If I move it to the left a little, it shows up. It's as if there is some clipping or something.
I am using TCPDF, and since I am needing to modify an existing PDF, I am also having to use the FPDI class. It appears to me that FPDI normally is integrated with FPDF, so I've been using the FPDF methods to build out my PDF. OK, so here is some of my code (or the relevant parts)...
$pdf = new PDF();
$pdf->AddPage( 'L', 'Letter' );
$pdf->SetAutoPageBreak(false);
$pdf->SetXY(261,200);
$pdf->Write(5, 'test');
There is at least a centimeter of whitespace to the right of the text when I position the text with a value of 260. If I move it just one more unit to 261, like in the code above, it just disappears. I'm able to position the text so far on the bottom of the page, that only the top half of the letters show, however, I can't even approach the right side of the page, or the text will completely disappear. I've set the SetAutoPageBreak to false, so new pages aren't created, and I've also flirted with zeroing out the margins.

Might be a bit late in the game...
I had a look at the fpdf.php file and it looks like it adds a margin of 1cm.
If you lower it then you can get text closer to the edge of the page. Below is the original line:
// Page margins (1 cm)
$margin = 28.35/$this->k;
But if you change it to something like
$margin = 10/$this->k;
This gets you closer to the edge of your document.

I've had the best luck using cells to position text, for some reason they have shown to be more accurate and easier to work with than simply writing text onto the document:
$pdf->SetXY(261,200);
$pdf->Cell(0,10,'My text',0,1, 'C');
Docs: http://www.fpdf.org/en/doc/cell.htm

Write() is used for flowing text (internally it uses several Cell() calls). If it reaches the right margin an automatic line break is done and the next word/character will start a new line at the left margin.
The word will not disappear but will be shown at the lower left area.
You can see the characters flowing with this simple script:
$pdf = new FPDF();
$pdf->AddPage( 'L', 'Letter' );
$pdf->SetAutoPageBreak(false);
$pdf->SetFont('Helvetica');
$pdf->SetXY(261,200);
$pdf->Write(5, 't e s t');
$pdf->Output();

Try the following:
$pdf->SetAutoPageBreak('auto',0);

Related

Convert Rich text from Tinymce and use it to fill a portion of a pdf doc

We have an application that takes text from a form (it's ultimately a spreadsheet) and pulls it from the database and creates a pdf document. Using fdpf and everything is working well. But there is a header portion of the doc that is currently plain text posting from a <texarea>, and we want to upgrade that portion to rich text using tinymce. I can easily use https://github.com/spipu/html2pdf to create a nice, full doc from the text, but it's only meant to be a small portion of the doc. This heading is not the "Header", which is taken from a jpg image.
I've tried several approaches including creating a separate doc with the rich text (html) portion and attempting to merge the two, which works great if the two are separate pages, but not so well when trying position one inside another when the one is of varying sizes, shapes, lines. Another thing I've tried is using imagemagick to convert the pdf taken from the rich text portion to a jpg and then inserting the image into the other pdf. This works great unless the heading contains mostly text(as it will).Images come through well but text becomes unreadable with my lack if image manipulation prowess.
using fpdf
class foo extends FPDF
{
public function fooBody ($bar) {
`````````````````````````````````
$data is obj containing db entities
current lines for the heading (having to remove html rn)
$data->heading = preg_replace("/ /",'',$data->heading);
$this->MultiCell(190, 3, trim(strip_tags($data->heading)), 0, 'L', 0);
$foo= new foo();
$foo->fooBody(bar);
add page...
output()..
etc.
wish I could just do something like below
$html2pdf->writeHTML($data34->heading);
$richTextHeading = $html2pdf->output('file.pdf', 'S');
foo->MultiCell(190, 3,$richTextHeading, 0, 'L', 0);
I want to use the same doc I have now with fpdf but somehow include some converted html for a small portion of it, but am currently only capable of having one (current doc) or the other (html doc).
If anyone comes across this thread, I ended up just using TCPDF, and re-writing my old code to work with TCPDF. Suprisingly I only need to change font names in a few places (Ariel->helvetica) and explicitly state cell height and margins. The old code worked mostly as is, and this
$this->MultiCell(190, 3, trim(strip_tags($data->heading)), 0, 'L', 0);
Is now simply this
$this->writeHTML( $data->heading);

TCPDF awful text rendering

Hy,
I have some images that I converto to PDF pages with TCPDF::Image, and then I add the text on another level, but the results I get rendering text with TCPDF are quite awful, this is how the text should look
And this is the rendered PDF
As you can see TCPDF is inserting some new line "randomly", And I can't understand why, I'm using tcpdf 6.2.6
this is my code
$pdf->SetFont($TCPDFFontFile, $fontStyle, $fontSize, '', false);
$pdf->setTextRenderingMode(0, true);
$pdf->setCellHeightRatio($lineHeight);
$pdf->SetTextColorArray($textColorArray);
$pdf->MultiCell(
$removedItem->width,
$removedItem->height,
$removedItem->text,
0,
$textAlign,
false,
1,
$left,
$right
);
Any ideas? Maybe a problem with the latest version? Even if I already tried with many other version like 6.1.0 or 6.2.0 but nothing changed...
EDIT: I noticed that there are differences even in the charater spacing, and even the height of the lines are slithly different, is this any help?

FPDF right margin values have no effect

I am using the PHP extension FPDF to create PDF documents. I believe I have the margins set to 1" all the way around with justified text, but when I create a PDF document, download it and open it in Acrobat, I see the left margin is 1" but the right margin is about 1.2". I've gone through fpdf.php looking for the issue and cannot find it.
$oPdf = new myPDF('P', 'mm', 'letter');
$oPdf->Open();
$oPdf->SetMargins(25.4,25.4,25.4,25.4);
//set default font/colors
$oPdf->SetFont('Times', '', 12);
$oPdf->SetTextColor(0,0,0);
$oPdf->SetFillColor(255, 255, 255);
//add the page
$oPdf->AddPage();
$oPdf->AliasNbPages();
If I change the top and left margin values, the document reflects the changes. If I change the bottom or right, there is no change. I've seen how the bottom can be changed wth set auto default page break, answered elsewhere. My question is how can I change the right margin and it actually take effect in my document? I have a feeling that this has to do with the measurement of the text when FPDF calculates whether the justified text will fit on the line. I've checked the width of the line and it outputs 165.1 (which is 6.5 inches x 25.4mm) Completely stumped.
Ok, I feel kind of dumb, but hopefully this will help others. I use the FpdfMulticell (See http://www.interpid.eu/fpdf-multicell) for more control over cells and other parts of displaying the content on the PDF document. This is great and all, except for the redundancies that are created. The components of this function require width and height for the cell to be created. This is where the problem was. For some reason I was passing 160 to it rather than 165.1. 6.5" x 25.4 = 165.1. When I go through the references to create the multiCell function within the class, it fixes my problem.
If you're going to use the multicell, I suggest declaring a variable at the beginning of your page such as $pw (i.e., page width) and then instead of passing a constant value, pass the variable. That way your values are uniform and if you want to change it up, then you only have 1 value to change. Make sure you comment so you know what the purpose of that variable is.
$oMulticell = new FpdfMulticell($oPdf);
$pw = 165.1
//Make sure that the content is long enough to go to another line or you won't
//notice the difference with the justified text
$content = "Write some text here Write some text here Write some text here Write some text here Write some text here Write some text here Write some text here Write some text here ";
$oMulticell->multiCell($pw,10,$content,0,"J",1,0,0,0,0);
This works!

Auto fitting a cell to the size of the content?

I'm new to tcpdf, creating my first document.
I wonder if there is a way to fit the width of the cell automatically to the content. I currently only see options for fixed size, or taking the whole page width until the end of the line.
I'm aware of GetStringWidth() but having the following problems with it
Why should one bother even for this? Is there a way to just make the cell fit automatically to its contents width?
GetStringWidth() seems to err from time to time, giving shorter results the actual, thus causing the text to be split to the next line. A font is set.
After learning TCPDF more, this is the conclusion:
Cell() and MultiCell() are not intended to be used for just outputting a string and fitting it's length. Instead, Write() and WriteHtml() should be used. Cells exist for the case where you actually want to control the dimentions of the field manually.
Nevertheless, in some cases one may want to compute the width of the cell, such that it takes into account the sizes of the text inside. For this purpose exists GetStringWidth(). (Unfortunately for me it err's from time to time. Maybe I'm not aware of something)
Have an internal "Legacy" application that uses TCPDF to generate a PDF of a checklist. We recently moved from creating a giant string of HTML that described a table, created using the $pdf->writeHTML($myHTMLString); method, to using the MultiCell() methods.
However, we ran into an issue where some text in a description cell would need to run on to a second line, this threw off our layout. As a fix, we created an if block based on 2 variables, one for the string width the other for the actual cell width. (We had 2 instances where the cell width might vary).
If block example:
// Get width of string
$lWidth = $pdf->GetStringWidth(strip_tags($clItem['description']));
// Determine width of cell
$oadWidth = (.01*$width[0])*186;
if ($lWidth < $oadWidth) {
$cHeight = 3.5;
} else {
$cHeight = 7;
}
We then used the variable created by the if block in the MultiCell() like this
$pdf->MultiCell((.01*$width[0])*186, $cHeight, strip_tags($clItem['description']), 1, 'L', 1, 0, '', '', true);
We reused the $cHeight variable for the height params in the other sibling cells so each row of cells had a uniform height. You could most likely reuse this method with any of the other right functions that have a height parameter in TCPDF. Thanks to #shealtiel for the original reference to GetStringWidth()

Draw color for text background PHP and GD

I've run into another problem with GD and PHP.
I'm successfully writing text to an image.
However, I've encountered a case where it would be beneficial to place the text - instead of directly on the image - on a rectangle (or any shape) to create a solid background for the text where the image it's being placed on might not allow the text to be read very easily.
My two ideas are, in order of preference:
Fill the background with the color as it writes the text
Write the text to an appropriately sized image with a solid background, and then overlay the image onto the target
I can't figure out how to do #1 and #2 seems overly complex and I don't know how to determine the dimensions of the text so that I can create a new image for it.
For clarity, here is the output that isn't very good:
And here's how I'd like it to look, with a tight box behind the text of any color:
I'm open to any suggestions, but drawing the color on the fly without any other images or hackiness would obviously be my first choice.
Update:
After #Dan suggested using `imagettftext', I decided that it was high time I added support for that function to my library. Everything is working as would be expected except for one major issue.
The text that's written to the image is still transparent, even when written to a solid background (0 transparency).
Here's a script I wrote to test:
<?php
set_include_path('backbone:global:jquery');
require_once('Image.php');
$scout = new Image();
$scout->source = "scout.jpg";
$result = $scout->Write->Font(25, 25, "A Fairly Long String", 12, "#FF0000", 0, "LiberationSans-Regular.ttf", 1, "#FFFF00", .4, 4);
if( !isset($_GET['dev']) )
{
header("Content-Type: " . $scout->contentType());
}
if( $result )
{
$scout->output();
}
?>
The files I used/required:
1. scout
2. liberation font
3. Image Manipulation Library
- Image
- ImageBase
- ImageCombine
- ImageDraw
- ImageManipulate
- ImageWrite
I apologize about all the files, it really only uses Image, ImageBase, ImageCombine, and ImageWrite, but the others are require_onceed by the loader.
Here's a sample of the output from the script above:
And here's output with zero transparency (fully opaque):
$result = $scout->Write->Font(25, 25, "A Fairly Long String", 12, "#FF0000", 0, "LiberationSans-Regular.ttf", 1, "#FFFF00", 1, 4);
Any ideas what could be causing this? It's EXTREMELY possible that it's my code somewhere, but it seems strange that it would work exactly as I thought it should except for this one bug.
In searching desperately for the answer to this problem, I stumbled upon this SO question that's tangentially related to my problem, and contains the answer.
I've never fully understood why you tell imagealphablending false when you want transparency, so I guess my failure to properly understand the code I'm using has led to this issue.
In any case, the following modified code works like a charm in my one single test case.
To write text to a background without forced 100% transparency for the character boxes, you must turn alpha blending ON while writing the text:
imagealphablending($text->handle, true);
$bool = imagettftext($text->handle, $textSize, $angle, $padding, abs($size[5]) + $padding, $this->AllocateColor($rgba[0]['r'], $rgba[0]['g'], $rgba[0]['b'], $rgba[0]['alpha']), $font, $string);
imagealphablending($text->handle, false);
Maybe this will do the job for you if you switch to ttf. http://php.net/manual/en/function.imagettfbbox.php

Categories