#1 2022-04-27 08:19:24

rvk
Member
Registered: 2022-04-14
Posts: 115

EmbeddedWholeTTF false with barcode fonts gives blocks

I'm now trying to tackle the reason why I can't use EmbeddedWholeTTF := false when using barcode fonts.
I already found this topic but the suggested hack to set isSymbolFont to true for that font doesn't work for me.
https://synopse.info/forum/viewtopic.php?id=6197

(the topic was not concluded with a solution)

*) First one little question. Embedding partial fonts (even fonts that work correctly like 'Segoe Script') are marked as "Embedded" and Encoding "Ansi" in the PDF. When I create this PDF with another creator I get "Embedded Subset" and encoding "Built-in". Could it be that subset embedding and/or encoding 'flag' isn't set correctly?

*) Then the barcode font. When using EmbeddedWholeTTF := true it works perfectly. When using EmbeddedWholeTTF := false I get blocks for Code3de9 and Code128. The KIXBarcode and SegoeScript work correctly. (but as stated below, all are marked as "Embedded" without the word "Subset" and all are encoding "Ansi".

Where can I look to debug this problem. Embedding the barcodes fully doesn't add much to the PDF but for SegoeScript it does. For what fonts is isSymbolFont to be set (what's it used for)? (But as stated, forcing this to true doesn't work for me)

(it somehow feels like the wrong letters are embedded.)

Used fonts: Tahoma (default in Windows), SegoeScript (default in Windows but not in EmbeddedTTFIgnore), Code128 and Code3de9, KIXBarcode.

procedure MakePdfSynPdf;
var
  FileTemp: string;
  Doc: TPdfDocumentGDI;
  Page: TPdfPage;
begin
  // if CheckC39 then; // For testing I installed this font for current users
  FileTemp := 'C:\Temp\Test2.pdf';
  Doc := TPdfDocumentGDI.Create;
  try
    Doc.AddTrueTypeFont('Code 3 de 9');
    Doc.EmbeddedTTF := true;
    Doc.EmbeddedTTFIgnore.Text := MSWINDOWS_DEFAULT_FONTS;

    Doc.EmbeddedWholeTTF := false; // why does this need to be true?

    Doc.Root.PageLayout := plSinglePage;
    Doc.NewDoc;
    Page := Doc.AddPage;
    Doc.VCLCanvas.TextOut(40, 40, 'Test1');
    Doc.VCLCanvas.TextOut(60, 60, 'Test2');

    Doc.VCLCanvas.Font.Name := 'Code 3 de 9';
    Doc.VCLCanvas.Font.size := 24;
    Doc.VCLCanvas.TextOut(80, 80, '*123456789*');    // blocks

    Doc.VCLCanvas.Font.Name := 'Code 128';
    Doc.VCLCanvas.Font.size := 24;
    Doc.VCLCanvas.TextOut(120, 120, '*123456789*');  // blocks

    Doc.VCLCanvas.Font.Name := 'KIX Barcode';
    Doc.VCLCanvas.Font.size := 12;
    Doc.VCLCanvas.TextOut(160, 160, '5569LB33');     // correct

    Doc.VCLCanvas.Font.Name := 'Segoe Script';
    Doc.VCLCanvas.Font.size := 14;
    Doc.VCLCanvas.TextOut(190, 190, 'Hello World');  // correct

    Doc.SaveToFile(FileTemp);
    // ExecAssociatedApp(FileTemp);
  finally
      Doc.Free;
  end;
end;

with EmbeddedWholeTTF := false;

XZ2luC4.png

with EmbeddedWholeTTF := true;

WvscxCR.png

Offline

#2 2022-04-27 08:39:27

rvk
Member
Registered: 2022-04-14
Posts: 115

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

I may have found the problem (or partially).

In SynPdf.pas there is the CreateFontPackage().
But the call is always called with TTFCFP_UNICODE_CHAR_SET.

When I change this to TTFCFP_SYMBOL_CHAR_SET the Code128 and Code3de9 gets embedded correctly.
But if I do that, the KIXBarcode and SegoeScript now incorrectly embedded.
So it needs to check what font is used to embed correctly.

(I'm not sure how to do that smile )

It's also strange Code128 and Code3de9 are not detected as 'symbol' fonts (whatever they are) but I'm not sure it matters if for the CreateFontPackage() the correct flag is used.

Documentation for CreateFontPackage():
https://docs.microsoft.com/en-us/window … ontpackage

Last edited by rvk (2022-04-27 08:42:14)

Offline

#3 2022-04-27 08:47:38

rvk
Member
Registered: 2022-04-14
Posts: 115

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

Calling CreateFontPackage() with the $FFFF { = TTFCFP_DONT_CARE } flag does fix it.

But that feels like a really ugly hack (but I'm not sure, I don't know if passing that flag is important).

if CreateFontPackage(pointer(ttf),ttfSize,
   SubSetData,SubSetMem,SubSetSize, usFlags,ttcIndex,TTFMFP_SUBSET,0,
   TTFCFP_MS_PLATFORMID, { TTFCFP_UNICODE_CHAR_SET } { TTFCFP_SYMBOL_CHAR_SET } $FFFF { = TTFCFP_DONT_CARE },
    pointer(Used.Values),Used.Count, @lpfnAllocate,@lpfnReAllocate,@lpfnFree,nil)=0 then begin

Result with EmbeddedWholeTTF true is 352KB. With EmbeddedWholeTTF false is 62KB smile

(Still, the ghostscript version is 17KB)

Last edited by rvk (2022-04-27 09:13:14)

Offline

#4 2022-04-27 08:56:18

rvk
Member
Registered: 2022-04-14
Posts: 115

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

BTW, in the documentation it says TTFCFP_FLAGS_COMPRESS isn't implemented yet.
But if I use TTFMFP_SUBSET or $0002 { TTFCFP_FLAGS_COMPRESS } the resulting PDF gets from 60KB downto 15KB.

So TTFCFP_FLAGS_COMPRESS is definitely implemented in Windows 10. The only question is if this compression can be used in the PDF because the result isn't entirely correct. But that's for another time wink

YNPjyto.png

Edit: It's not TTFCFP_FLAGS_COMPRESS that is implemented (it still does nothing). I inadvertently put this in the usSubsetFormat parameter. And then $0002 stands for TTFCFP_DELTA. It does show that only the changed extra characters do not take much space. It's the initial ttf data with copyright info and certificates etc that take up so much space. Other generators stript this information (running it through an optimizer does the same).

Last edited by rvk (2022-04-27 21:22:08)

Offline

#5 2022-04-27 10:29:28

ab
Administrator
From: France
Registered: 2010-06-21
Posts: 14,655
Website

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

TTFCFP_DONT_CARE seems to be the way to go.
Please try https://synopse.info/fossil/info/a4eaf1c539

Also try to enable PDF 1.5 layout for a slightly smaller resulting file.

For TTFCFP_FLAGS_COMPRESS we could see in the future. wink

Online

#6 2022-04-27 17:15:02

rvk
Member
Registered: 2022-04-14
Posts: 115

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

Yes. It works fine now with TTFCFP_DONT_CARE. Glad to hear using "DONT_CARE" is no problem.

Using PDF 1.5 gives a slightly smaller file but not much.
PDF 1.3 gives 61,69 KB while PDF 1.5 gives 59,76 KB
Ghostscript gives 17,28 KB for PDF 1.3.

But at least the embedding of subset is much better now (was 352 KB).
Still, the SynPDF gives "Embedded" without the "Subset" keyword after is. Not sure why that is.

If I get any ideas about further compression I will let you know wink

(I'll also post a small note in the other topic to let Sven know.)

Thanks.

Edit: Looking at pdffonts from xpdf-tools you see that for Ghostscript (Temp0.pdf) the fonts are embedded but also Subsetted and Unicode.
Subsetted codes need to be proceeded by 6 random character followed by a + sign.
The fonts in Temp1.pdf from SynPdf are not marked as subsetted and are also not embedded as unicode.
Maybe it doesn't really matter (it seems to work fine) but I reckon this is not strict according to the rules wink

S:\pdfs\xpdf-tools-win-4.02\bin32>pdffonts -loc c:\temp\Test0.pdf
Config Error: No display font for 'Symbol'
Config Error: No display font for 'ZapfDingbats'
name                                           type              emb sub uni prob object ID location
---------------------------------------------- ----------------- --- --- --- ---- --------- --------
RDZRPI+Code128                                 TrueType          yes yes yes          12  0 embedded
UFQSLH+KIXBarcode                              TrueType          yes yes yes          14  0 embedded
ZRSKVS+SegoeScript                             TrueType          yes yes yes          16  0 embedded
UFQSLH+Tahoma                                  TrueType          yes yes yes           8  0 embedded
RDZRPI+Code3de9                                TrueType          yes yes yes          10  0 embedded

S:\pdfs\xpdf-tools-win-4.02\bin32>pdffonts -loc c:\temp\Test1.pdf
Config Error: No display font for 'Symbol'
Config Error: No display font for 'ZapfDingbats'
name                                           type              emb sub uni prob object ID location
---------------------------------------------- ----------------- --- --- --- ---- --------- --------
Tahoma                                         TrueType          no  no  no            6  0 external: C:\WINDOWS\Fonts\tahoma.ttf
Code3de9                                       TrueType          yes no  no            8  0 embedded
Code128                                        TrueType          yes no  no           10  0 embedded
KIXBarcode                                     TrueType          yes no  no           12  0 embedded
SegoeScript                                    TrueType          yes no  no           14  0 embedded

Edit #2: Yes. Doing this
    FFontDescriptor.AddItem('FontName','ABCDEF+' + FName);
with an ugly hack again, the fonts are marked as Subset.
Of course they all need to be randomized and only for subsetted fonts but you get the point.

Is the fact that they are embedded as Ansi a problem?
(Not sure why the Ghostscript variant is encoded as "Built-in" or what built-in actually means.)

(I hope you don't get sick of me smile )

Last edited by rvk (2022-04-27 17:48:44)

Offline

#7 2022-04-27 17:59:24

rvk
Member
Registered: 2022-04-14
Posts: 115

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

Yikes,
According to the PDF Tahoma should be replaced and not EMBEDDED.
But if I use pdftops to extract the pdf I see that Tahoma is STILL embedded.
That's the reason the PDF is so large.

So even with the fact a font is not supposed to be embedded (and is not used as embedded in the PDF) the font information is still inside the PDF (in the /sfnts part).

If I have some time tonight I'll find out why it's still in there.
Maybe it's an artifact from pdftops but i'll find out.

Edit: Probably false alarm. Via another stream debugger I see 4 fonts of which the SegoeScript is the largest one.
So Tahoma should not be embedded (and pdftops probably extract the local Windows font into the ps).
You can ignore this post.

Last edited by rvk (2022-04-27 19:31:23)

Offline

#8 2022-04-28 14:04:29

rvk
Member
Registered: 2022-04-14
Posts: 115

Re: EmbeddedWholeTTF false with barcode fonts gives blocks

I have implemented some improvements when embedding subset of a default Microsoft font. I saw those font include a LOT of information that is not needed in a PDF so the TTF information can be made much smaller. If I have some more time I'll post the cleaned up changes/code in a separate topic.

I also made en effort to mark embedded subset fonts correctly in a PDF. Subsets need 6 random uppercase character plus a + sign in front of the name according to the official documentation. I'll also post this in a separate topic.

Offline

Board footer

Powered by FluxBB