En PDF, hvis overskrift bærer en graduering-baggrund i Word- eller Excel-stil, renderet til et billede, plejede at komme tilbage med et tomt hvidt rektangel, hvor farveblandingen skulle være. HotPDF's siderenderer respekterer nu PDF-sh (shading)-operatoren for Type 2 aksiale og Type 3 radiale gradueringer: Den evaluerer shadingens funktion langs gradueringsaksen og maler blandingen, hvor tidligere versioner lydløst sprang operatoren over og efterlod området papirhvidt. De to shading-typer, der dækker næsten enhver kontordokumentgraduering, er inkluderet; mesh-typerne er ikke, og denne artikel er ærlig om, hvor denne linje falder
Hvorfor renderer en PDF-graduering som en hvid boks?
En PDF-graduering er en vektorkonstruktion, ikke et bitmap, som rendereren kan overføre. En shading-ordbog (ISO 32000-1 §8.7.4.5) beskriver geometrien — en akse eller et par cirkler i Coords-arrayet — plus en farvefunktion, og sh-operatoren maler denne shading over det aktuelle klippeområde, den samme grafikmodel, som HotPDF eksponerer, når du tegner stier og udfyldninger på et sidelærred. HotPDF's siderenderer gennemgår indholdsstrømmen operator for operator, og enhver operator, den ikke har en kodevej til, springes over, så resten af siden stadig renderer. Før version 2.335.0 levede sh i dette overspringne sæt: En overskrift- eller fuldsidesgraduering bidrog ikke med noget til outputtet, så baggrunden fremstod som hvid. Filen var aldrig beskadiget. Rendereren havde simpelthen ingen håndtering af netop den operator, og en hvid boks er præcis, hvad en manglende håndtering ser ud som
Funktionsevalueringskæden bag en shading
Type 2 aksiale og Type 3 radiale shadings bærer begge en /Function, der kortlægger en parametrisk position langs gradueringen til en farve (ISO 32000-1 §7.10), og HotPDF's funktionsevaluator opløser FunctionType og fordeler ud fra den. Type 2 eksponentiel interpolation (§7.10.3) beregner C0 + t^N * (C1 - C0) med Domain- og Range-begrænsning; Type 0 sampled-funktioner (§7.10.2) læser et gitter af 8-, 16- eller 32-bit stikprøver og vælger den nærmeste via Encode-kortet, det tilfælde der er dækket i dybden i vores gennemgang af Type 0 sampled farveopslag; Type 3 stitching-funktioner (§7.10.4) vælger en underfunktion ud fra Bounds-arrayet og kører rekursivt ind i den. Type 4 PostScript-beregnerfunktioner (§7.10.5) evalueres ikke — de nedgraderes yndefuldt til en mislykket evaluering i stedet for en forkert farve, hvilket matcher den konservative politik, som HotPDF anvender på tværs af renderstien. Denne evaluator blev leveret i version 2.334.0, en udgivelse før selve operatoren, fordi shading-maleren kun er så god som den underliggende funktion
Hvordan forvandler HotPDF en kontinuerlig graduering til pixels?
HotPDF tilnærmer den kontinuerlige blanding med en endelig række af ensfarvede bånd. Shading-maleren gennemgår gradueringsaksen, opdeler den i op til 64 bånd — færre når aksen er kort i enhedspixels — evaluerer funktionen ved hvert bånds parametriske position og udfylder et rektangel vinkelret på aksen med en ensfarvet pensel. Afvejningen er båndantal mod blødhed: Flere bånd sporer blandingen tættere, men koster flere udfyldninger, og 64 is det bevidste loft. Fordi antallet også skalerer med akselængden i enhedspixels, betyder opløsningen noget. Rendering af den samme side ved en højere DPI forlænger aksen, så en kort graduering får flere bånd, og dens striber blødes op, indtil loftet nås
// The shading discretizer uses up to 64 color bands along the gradient
// axis, but never more than the axis is long in device pixels. Rendering
// the same page at a higher DPI lengthens that axis, so a short gradient
// gains bands and the banding softens until the 64-band ceiling is hit.
Thumb := Pdf.RenderLoadedPageToBitmap(PageIndex, 96); // coarser bands
Proof := Pdf.RenderLoadedPageToBitmap(PageIndex, 300); // up to 64 bands
Rendering af en shaded side til et bitmap
Det offentlige indgangspunkt er uændret: RenderLoadedPageToBitmap tager et 0-baseret sideindeks og en DPI-værdi, returnerer et kalder-ejet 24-bit bitmap og returnerer nil ved fejl i stedet for at rejse en undtagelse, så shading-understøttelsen er gennemsigtig for kode, du allerede har. En side, der plejede at renderes med sin graduerings-overskrift tom, returnerer nu det samme bitmap med blandingen malet ind, og der er ikke brug for nogen API-ændring for at få det. Den eneste ting, der er værd at huske, er ejerskab: Kalderen frigør det returnerede bitmap. Den fulde renderingspipeline — fortolkning af indholdsstrøm, indlejrede glyfer og sidecaching — er dækket i vejledningen til rendering af PDF-sider til et bitmap i Delphi
var
Pdf: THotPDF;
Bmp: TBitmap;
begin
Pdf := THotPDF.Create(nil);
try
if Pdf.LoadFromFile('quarterly-report.pdf') > 0 then
begin
// Page 1 (zero-based) at 150 DPI. A gradient-filled header that
// used to come back blank now carries its color blend.
Bmp := Pdf.RenderLoadedPageToBitmap(0, 150);
if Assigned(Bmp) then
try
Bmp.SaveToFile('page1.bmp');
finally
Bmp.Free;
end;
end;
finally
Pdf.Free;
end;
end;
Et billigt regressionsværn falder ud af det samme kald. Render siden, prøv en pixel, hvor gradueringsbåndet hører til, og bekræft, at det ikke længere er det papirhvide, som rendereren plejede at falde tilbage til — et enkeltlinjetjek, der fanger en lydløs returnering til den gamle no-op-adfærd
Bmp := Pdf.RenderLoadedPageToBitmap(0, 150);
if Assigned(Bmp) then
try
// True when the sh operator painted; False if the region fell back to white.
HeaderPainted := Bmp.Canvas.Pixels[Bmp.Width div 2, 8] <> clWhite;
finally
Bmp.Free;
end;
Hvor HotPDF ikke maler: Mesh-shadings og klippekanter
De fire mesh-shading-typer er uden for anvendelsesområdet, og et dokument bør vide det på forhånd. Fritformede Gouraud-trekantmasker (Type 4), gitterformede Gouraud-masker (Type 5), Coons-lappemasker (Type 6) og tensorprodukt-lappemasker (Type 7), der er defineret i ISO 32000-1 §8.7.4.5.5 til §8.7.4.5.8, renderes ikke; en side, der bruger en af dem, renderes stadig, blot efterlades dette område, som det er. Yderligere to kanter er værd at sige tydeligt: Båndrektanglerne dækker shadingens stribe i stedet for at blive klippet nøjagtigt til den aktuelle klipningssti, så en graduering maskeret i en afrundet eller uregelmæssig form maler som sin afgrænsende stribe, indtil præcis områdeklipning ankommer i en senere runde. HotPDF antager også, at funktionsoutputtet er RGB eller gråtoner, så en shading oprettet i CMYK eller et eksotisk farverum tilnærmes i stedet for at være farvestyret. For de dokumenter, som de fleste Delphi- og C++Builder-teams rent faktisk behandler — rapporter, fakturaer, kontoudtog og diasshows eksporteret til PDF — aksial og radial dækker stort set enhver graduering, du vil møde, og mesh-tunge designkorrekturark er det tilfælde, der skal behandles som en forhåndsvisning snarere end en korrektur
HotPDF's siderenderer, supporten til sh-operatoren beskrevet her, og Type 0/2/3-funktionsevaluatoren under den leveres som en del af HotPDF Component til Delphi og C++Builder — et indfødt VCL-bibliotek uden eksterne DLL-afhængigheder, der dækker PDF-oprettelse, redigering, tekstudtrækning og siderendering i én pakke