M5: a button caption's characters its font's encoding can't hold are reported

This commit is contained in:
Eric Kaden
2026-10-19 17:25:19 -04:00
parent 24a45db045
commit 0ca7fb9be9
2 changed files with 21 additions and 1 deletions
+1 -1
View File
@@ -230,7 +230,7 @@ pub(crate) fn button_caption(doc: &Document, da: &str, caption: &str, width: f64
Some((o, enc)) => (da.font.clone(), o, enc),
None => ("Helv".to_string(), helvetica(), FontText::WinAnsi),
};
let missing = if enc == FontText::WinAnsi { pdfcraft_fonts::first_undrawable(caption) } else { None };
let missing = enc.first_unencodable(caption);
let size = if da.size > 0.0 { da.size } else { auto };
let tw = enc.width(caption, size);
let mut out =
+20
View File
@@ -111,6 +111,26 @@ fn a_button_caption_is_drawn_in_its_fields_font_size_and_color() {
assert!(auto.contains("/Helv 14.00 Tf") && auto.contains(" 0 g"), "{auto}");
}
#[test]
fn a_button_caption_its_fonts_encoding_cant_hold_is_reported() {
let objs: Vec<String> = vec![
"<< /Type /Catalog /Pages 2 0 R /AcroForm 4 0 R >>".into(),
"<< /Type /Pages /Kids [3 0 R] /Count 1 /MediaBox [0 0 600 800] >>".into(),
"<< /Type /Page /Parent 2 0 R /Annots [7 0 R] >>".into(),
"<< /Fields [7 0 R] /DA (/Helv 0 Tf 0 g) /DR << /Font << /Helv 5 0 R /CN 6 0 R >> >> >>".into(),
"<< /Type /Font /Subtype /Type1 /BaseFont /Helvetica /Encoding /WinAnsiEncoding >>".into(),
"<< /Type /Font /Subtype /Type0 /BaseFont /STSong-Light /Encoding /UniGB-UCS2-H /DescendantFonts [<< /Type /Font /Subtype /CIDFontType0 /BaseFont /STSong-Light /CIDSystemInfo << /Registry (Adobe) /Ordering (GB1) /Supplement 4 >> >>] >>".into(),
// A UCS-2 CMap holds 签 but not a character beyond U+FFFF, which is drawn as `?`.
"<< /Type /Annot /Subtype /Widget /FT /Btn /T (go) /Ff 65536 /DA (/CN 9 Tf 0 g) /MK << /CA <FEFF7B7E>> >> /Rect [50 700 140 711] /P 3 0 R >>".into(),
];
let mut doc = document(&objs);
redraw_field(&mut doc, "go").unwrap();
assert!(undrawn_fields(&doc).is_empty(), "签 is drawn");
set_props(&mut doc, "go", &FieldProps { caption: Some((0, "签\u{2000B}".into())), ..Default::default() }).unwrap();
assert!(ap(&doc, &field(&fields(&doc), "go").widgets[0]).contains("/CN 9.00 Tf"));
assert_eq!(undrawn_fields(&doc), [("go".to_string(), '\u{2000B}')]);
}
#[test]
fn button_caption_preserves_other_widgets_and_shared_dictionaries() {
for indirect_caption in [false, true] {