Przejdź do głównej zawartości

Rozwiązywanie problemów z czcionkami, podzbiorami i tagowaniem

Te wpisy opisują niepowodzenia wykrywania i parsowania czcionek zgłaszane przez NextPDF\Exception\FontNotFoundException i NextPDF\Exception\FontParsingException. Obejmują też diagnostykę pokrycia chińskiego, japońskiego i koreańskiego (CJK) oraz problemy z drzewem struktury, które wpływają na tagowane wyjście. Każdy wpis wskazuje dokładny wyjątek lub test, dzięki czemu można zweryfikować przyczynę.

  • Objaw. FontNotFoundException z komunikatem w postaci Font "<name>" not found. Searched: [<paths>].
  • Prawdopodobna przyczyna. Żądana rodzina czcionek albo ścieżka pliku nie istnieje, jest nieczytelna lub znajduje się w katalogu czcionek niedostępnym dla środowiska uruchomieniowego. Dane czcionki mogą być poprawne, ale silnik nadal nie może uzyskać do nich dostępu.
  • Dowody / diagnoza. getContext() zwraca font_name, search_paths i fallback_attempted. Użyj search_paths, aby sprawdzić każdą lokalizację, którą silnik wypróbował. Użyj fallback_attempted, aby potwierdzić, czy użycie czcionki zapasowej zostało już wypróbowane.
  • Rozwiązanie.
    1. Porównaj żądaną wartość font_name z faktycznie obecnym plikiem czcionki.
    2. Dodaj katalog zawierający czcionkę do skonfigurowanych katalogów czcionek lub popraw przekazaną ścieżkę.
    3. Sprawdź, czy użytkownik środowiska uruchomieniowego może odczytać plik.
    4. Uruchom wywołanie ponownie.
  • Powiązane. Dokumentacja wyjątków.
  • Objaw. FontParsingException z komunikatem w postaci Failed to parse font file "<file>": <reason>.
  • Prawdopodobna przyczyna. Silnik znalazł plik czcionki, lecz nie może wykorzystać jego zawartości: obcięty nagłówek, nieprawidłowy katalog tablic albo brak obowiązkowej tablicy, takiej jak head, hhea lub OS/2.
  • Dowody / diagnoza. getContext() zwraca font_file i parse_error. parse_error wskazuje problem strukturalny.
  • Rozwiązanie.
    1. Odczytaj parse_error, aby zidentyfikować defekt strukturalny.
    2. Zastąp plik czcionki zweryfikowaną kopią tego samego kroju.
    3. Uruchom wywołanie ponownie.
  • Powiązane. Dokumentacja wyjątków.

Wpis: tworzenie podzbioru nie powiodło się z powodu uszkodzonej tablicy czcionki

Dział zatytułowany „Wpis: tworzenie podzbioru nie powiodło się z powodu uszkodzonej tablicy czcionki”
  • Objaw. FontParsingException, gdy font_file ma wartość font-subset, a parse_error ma wartość taką jak Invalid head table: too short, Invalid hhea table: too short, Invalid maxp table: too short lub Failed to unpack font data.
  • Prawdopodobna przyczyna. Czcionka przeszła początkowe wczytanie, lecz tablica potrzebna do utworzenia podzbioru jest obcięta lub nie można jej rozpakować. Mechanizm tworzenia podzbiorów odrzuca czcionkę, zamiast wygenerować uszkodzony podzbiór.
  • Dowody / diagnoza. Jeśli tablica head, hhea lub maxp jest zbyt krótka albo rozpakowanie się nie powiedzie, src/Typography/FontSubsetter.php zgłasza FontParsingException, podając jako nazwę pliku dosłowny token font-subset. Token informuje, że niepowodzenie wystąpiło podczas tworzenia podzbioru, a nie podczas początkowego wczytywania.
  • Rozwiązanie.
    1. Zastąp źródłową czcionkę kompletną, nieobciętą kopią tego samego kroju.
    2. Jeśli czcionkę generuje narzędzie kompilacji, wygeneruj ją ponownie i sprawdź, czy tablice head, hhea i maxp są kompletne.
    3. Uruchom kompilację ponownie.
  • Powiązane. Walidacja PDF/A i PDF/UA.
  • Objaw. Tekst chiński, japoński lub koreański renderuje się jako puste prostokąty lub brakujące znaki, a pokrycie CJK przez czcionkę jest niepewne.
  • Prawdopodobna przyczyna. Wybrana czcionka nie obejmuje bloków Unicode wymaganych przez dane pismo. Każde pismo CJK wymaga określonych bloków oprócz wspólnych bloków ideogramów.
  • Dowody / diagnoza. src/Typography/CjkFontValidator.php udostępnia validateCoverage(FontInfo $font, CjkScript $script). Metoda zwraca CjkCoverageResult z odsetkiem pokrycia oraz listą bloków poniżej 50% progu raportowania. Walidator próbkuje punkty kodowe. Jest narzędziem diagnostycznym i nie zmienia wczytywania czcionek.
  • Rozwiązanie.
    1. Uruchom CjkFontValidator::validateCoverage() dla danej czcionki i docelowego pisma.
    2. Odczytaj missingRanges, aby zobaczyć, które bloki nie są pokryte, na przykład Bopomofo dla chińskiego tradycyjnego, hiragana i katakana dla japońskiego oraz sylaby hangul dla koreańskiego.
    3. Wybierz czcionkę obejmującą te bloki lub dodaj czcionkę zapasową, która je obejmuje.
    4. Uruchom renderowanie ponownie i ponownie sprawdź pokrycie.
  • Powiązane. Dokumentacja wyjątków.

Wpis: predefiniowana mapa CMap nie pasuje do pisma CJK

Dział zatytułowany „Wpis: predefiniowana mapa CMap nie pasuje do pisma CJK”
  • Objaw. Tekst CJK mapuje się na niewłaściwe glify lub dokument używa predefiniowanej mapy CMap, która nie pasuje do jego języka.
  • Prawdopodobna przyczyna. Wykryte pismo określa nazwę predefiniowanej mapy CMap firmy Adobe. Czcionka obejmująca tylko wspólny blok ideogramów, bez bloku specyficznego dla pisma, jest zgodnie z założeniem wykrywana jako chiński uproszczony.
  • Dowody / diagnoza. CjkFontValidator::detectScript() zwraca wykryte pismo, a resolvePredefinedCMapName() je mapuje: chiński uproszczony na UniGB-UTF16-H, chiński tradycyjny na UniCNS-UTF16-H, japoński na UniJIS-UTF16-H i koreański na UniKS-UTF16-H. Jeśli nie ma żadnego bloku specyficznego dla pisma, wykrywanie wraca do chińskiego uproszczonego.
  • Rozwiązanie.
    1. Potwierdź, że czcionka zawiera blok specyficzny dla pisma: Bopomofo dla chińskiego tradycyjnego, hiragana lub katakana dla japońskiego oraz hangul dla koreańskiego.
    2. Jeśli dokument jest w chińskim tradycyjnym, lecz czcionka nie ma bloku Bopomofo, wybierz czcionkę, która go zawiera, aby wykrywanie rozpoznało zamierzone pismo.
    3. Uruchom renderowanie ponownie.
  • Powiązane. Dokumentacja wyjątków.

Wpis: tagowana zawartość nie tworzy użytecznego drzewa struktury

Dział zatytułowany „Wpis: tagowana zawartość nie tworzy użytecznego drzewa struktury”
  • Objaw. Kompilacja z tagowaniem nie tworzy drzewa struktury lub kolejna kontrola dostępności zgłasza puste albo brakujące drzewo struktury.
  • Prawdopodobna przyczyna. Kompilacja wygenerowała zawartość poza ścieżką tagowania, więc nie utworzyła żadnych elementów struktury. Drzewo struktury pozostaje puste.
  • Dowody / diagnoza. src/Accessibility/StructureTree.php i src/Accessibility/TaggedContentEmitter.php budują drzewo struktury z tagowanej zawartości. Test tests/Integration/Accessibility/EmptyTaggedPdfDoesNotAdvertisePdfUa2Test.php potwierdza, że puste drzewo struktury nie deklaruje zgodności z PDF/UA-2.
  • Rozwiązanie.
    1. Potwierdź, że zawartość jest generowana przez ścieżkę tagowania, aby elementy struktury były tworzone.
    2. Sprawdź, czy każda sekwencja oznaczonej zawartości jest mapowana na element struktury.
    3. Uruchom kompilację ponownie i sprawdź drzewo struktury.
  • Powiązane. Walidacja PDF/A i PDF/UA.

Wpis: znacznik języka elementu struktury jest odrzucany

Dział zatytułowany „Wpis: znacznik języka elementu struktury jest odrzucany”
  • Objaw. Kompilacja kończy się niepowodzeniem, ponieważ wartość języka w elemencie struktury lub w dokumencie nie jest prawidłowym znacznikiem.
  • Prawdopodobna przyczyna. Podana wartość języka nie jest prawidłowym znacznikiem BCP 47. Walidator odrzuca nieprawidłowe znaczniki, zamiast je generować.
  • Dowody / diagnoza. src/Accessibility/Bcp47Validator.php sprawdza poprawność znacznika. Nieprawidłowy znacznik powoduje zgłoszenie src/Accessibility/InvalidBcp47TagException.php. tests/Unit/Conformance/PdfUa2Section844LangStrictTest.php sprawdza rygorystyczny wymóg językowy PDF/UA-2.
  • Rozwiązanie.
    1. Zastąp wartość języka prawidłowym znacznikiem BCP 47, takim jak en-US, de-DE lub zh-Hant-TW.
    2. Ustaw język na konkretnym elemencie struktury, gdy język fragmentu różni się od języka dokumentu.
    3. Uruchom kompilację ponownie.
  • Powiązane. Walidacja PDF/A i PDF/UA.
  • FontNotFoundException i FontParsingException zgłaszają różne niepowodzenia. Pierwszy przypadek oznacza, że nie udało się uzyskać dostępu do pliku. Parsowanie oznacza, że plik został odczytany, ale jego bajty nie nadają się do użycia. Odczytaj klasę wyjątku, aby ustalić, które niepowodzenie wystąpiło.
  • font-subset w font_file to celowy znacznik etapu tworzenia podzbioru, a nie rzeczywista ścieżka. Nie szukaj pliku o nazwie font-subset.
  • CjkFontValidator próbkuje punkty kodowe, zamiast sprawdzać każdy z nich, więc jego wartość pokrycia jest szacunkiem na potrzeby doboru czcionki, a nie audytem dokładnym co do bajta.
  • Puste drzewo struktury jest zgodnie z założeniem raportowane jako niezgodne z PDF/UA-2. Jest to udokumentowane zachowanie silnika, a nie defekt.

Słowniczek: tworzenie podzbioru czcionek · pokrycie CJK · drzewo struktury