You are not logged in.
Hi,
after having used SynPDF for years without any issues, I stumbled upon a small problem today which leads to corrupted PDFs. I found out what's happening, but not sure about the proper solution.
So basically, my application tried to create a pdf that contains a Bitmap with a height of 1 pixel. In the procedure TPdfEnum.DrawBitmap, the bitmap size R is rescaled to variable Box in the function BoxI/RectI. But this rescaling results in a height of 0, which then leads to a corrupted PDF file (often, the PDF ends up corrupt, and if not, it usually does not continue drawing any elements that were added after the bitmap).
1. Why are both the right and bottom coordinates for variable Box shifted by -1 in function RectI?
2. Maybe there should be some error handling when height or width of the variable Box is 0, or the bitmap should not be drawn at all?
See the code section below. variable ClipRc is checked if it's actually a valid rectangle, but variable Box is not.
// draw the bitmap on the PDF canvas
with Canvas do begin
R := Rect(xd, yd, wd+xd, hd+yd);
NormalizeRect(R);
Box := BoxI(R,true);
ClipRc := GetClipRect;
if (ClipRc.Width>0) and (ClipRc.Height>0) then
Doc.CreateOrGetImage(B, @Box, @ClipRc) else // use cliping
Doc.CreateOrGetImage(B, @Box, nil);
// Doc.CreateOrGetImage() will reuse any matching TPdfImage
// don't send bmi and bits parameters here, because of StretchDIBits above
end;
Offline
1. Why are both the right and bottom coordinates for variable Box shifted by -1 in function RectI?
AFAIR it is because PDF boxes coordinates expect that.
2. Maybe there should be some error handling when height or width of the variable Box is 0, or the bitmap should not be drawn at all?
I guess the bitmap should not be drawn at all... what do you think?
Offline
I guess the bitmap should not be drawn at all... what do you think?
In my case, I do have such a bitmap that contains information I need on the pdf (might seem silly, but that's how it is, and I have to work with that). So just not drawing is not an option for me.
AFAIR it is because PDF boxes coordinates expect that.
I'll try to look further into that later this week, it seems a bit peculiar.
Offline
Hi Marsh,
the problem is not the BoxI function, but the starting rect R.
It should be 1px bigger than bitmap because the BoxI expect a rect with right and bottom border excluded.
change:
R := Rect(xd, yd, wd + xd, hd + yd);
in:
R := Rect(xd, yd, wd + xd + 1, hd + yd + 1);
With images larger or higher than 1px, you do not see the problem because the image is not "truncated" for the missing pixel but it is painted a (very) little stretched
If you try placing two normal bitmaps one over the other,
you should notice that with inflated rect, the draw will reach the correct right-bottom corner.
If you prefer not to modify existing behaviour for all pictures you can simply use:
if wd=1 then Inc(wd);
if hd=1 then Inc(hd);
R := Rect(xd, yd, wd + xd, hd + yd);
have a nice day
Last edited by MtwStark (2018-03-22 17:42:57)
Offline