Subject: | prTTFont causing "Warning: stream Length incorrect" |
Sometimes if a PDF is created using prTTFont to embed characters in a TrueType font, the resulting document will have an invalid stream length. Different PDF reader software will react in different ways to the invalid stream length - some programs emit warnings, others refuse to open the document.
The cause seems to be a missing newline character before the 'endstream' marker that terminates the stream containing the subsetted font glyph definitions. The code which appends the 'endstream' marker adds a newline character before 'endstream', but only if the stream did not already end with either a carriage return or a line feed. Since the stream is randomish binary bytes there's a 2-in-256 chance that a particular font subset will cause the newline to not be added.
On my Debian (Wheezy or Jessie) systems this code consistently produces a PDF which shows the problem:
my $arial_bold = '/usr/share/fonts/truetype/msttcorefonts/Arial_Bold.ttf';
my $text = 'ABCNOPSTWacdeghilmnoprstuwxyz012345679,@:/.';
prInitVars();
prFile('test.pdf');
blackText();
prTTFont($arial_bold);
prFontSize(13);
prText(60, 700, $text);
prEnd();
One way to confirm the error is to convert the PDF to a PNG using ImageMagick(which uses Ghostscript):
convert -density 100 -flatten -background white test.pdf test.png
and emits this message:
**** Warning: stream Length incorrect.
The problem code it not actually in PDF::Reuse at all - it's in Text::PDF which is used for TTF font support. I'm only logging this ticket here to help people who might encounter this problem when using PDF::Reuse.
This patch works around the problem for me but I'm not sure if it causes additional problems for PDF::Text:
=======================================================
--- lib/Text/PDF/Dict.pm 2006-03-17 22:39:17.000000000 +1300
+++ lib/Text/PDF/Dict.pm 2015-05-30 08:36:15.324799534 +1200
@@ -164,7 +164,7 @@
$pdf->out_obj($self->{'Length'}) if ($self->{'Length'}->is_obj($pdf));
}
}
- $fh->print("\n") unless ($str =~ m/$cr$/o);
+ $fh->print("\n");
$fh->print("endstream");
# $self->{'Length'}->outobjdeep($fh);
} elsif (defined $self->{' streamfile'})
=======================================================
It's not clear if PDF::Text is still being actively maintained. I've sent the above patch to Martin Hosken and will update here if a new release fixes the problem.
Regards
Grant