read_fonts/tables/
gdef.rs1pub use super::layout::{ClassDef, CoverageTable, DeviceOrVariationIndex};
6
7use super::layout::header::HeaderOffset;
8use super::variations::ItemVariationStore;
9
10#[cfg(test)]
11#[path = "../tests/test_gdef.rs"]
12mod tests;
13
14use crate::types::Compatible;
15
16include!("../../generated/generated_gdef.rs");
17
18impl<'a> Gdef<'a> {
19 fn select_offset(
20 &self,
21 original: Nullable<Offset16>,
22 extended: Option<Nullable<Offset32>>,
23 ) -> Result<HeaderOffset, ReadError> {
24 HeaderOffset::select(original, extended, self.version().compatible((1, 4)))
25 }
26
27 fn resolve_selected<T: FontRead<'a, Args = ()>>(
28 &self,
29 original: Nullable<Offset16>,
30 extended: Option<Nullable<Offset32>>,
31 ) -> Option<Result<T, ReadError>> {
32 match self.select_offset(original, extended) {
33 Ok(offset) => offset.resolve(self.offset_data()),
34 Err(error) => Some(Err(error)),
35 }
36 }
37
38 pub fn glyph_class_def(&self) -> Option<Result<ClassDef<'a>, ReadError>> {
40 self.resolve_selected(
41 self.glyph_class_def_offset(),
42 self.glyph_class_def2_offset(),
43 )
44 }
45
46 pub fn original_glyph_class_def(&self) -> Option<Result<ClassDef<'a>, ReadError>> {
48 self.glyph_class_def_offset().resolve(self.offset_data())
49 }
50
51 pub fn attach_list(&self) -> Option<Result<AttachList<'a>, ReadError>> {
53 self.resolve_selected(self.attach_list_offset(), self.attach_list2_offset())
54 }
55
56 pub fn original_attach_list(&self) -> Option<Result<AttachList<'a>, ReadError>> {
58 self.attach_list_offset().resolve(self.offset_data())
59 }
60
61 pub fn mark_attach_class_def(&self) -> Option<Result<ClassDef<'a>, ReadError>> {
63 self.resolve_selected(
64 self.mark_attach_class_def_offset(),
65 self.mark_attach_class_def2_offset(),
66 )
67 }
68
69 pub fn original_mark_attach_class_def(&self) -> Option<Result<ClassDef<'a>, ReadError>> {
71 self.mark_attach_class_def_offset()
72 .resolve(self.offset_data())
73 }
74
75 pub fn mark_glyph_sets_def(&self) -> Option<Result<MarkGlyphSets<'a>, ReadError>> {
77 self.resolve_selected(
78 self.mark_glyph_sets_def_offset().unwrap_or_default(),
79 self.mark_glyph_sets_def2_offset(),
80 )
81 }
82
83 pub fn original_mark_glyph_sets_def(&self) -> Option<Result<MarkGlyphSets<'a>, ReadError>> {
85 self.mark_glyph_sets_def_offset()
86 .unwrap_or_default()
87 .resolve(self.offset_data())
88 }
89}
90
91#[derive(Clone)]
93pub enum SelectedLigCaretList<'a> {
94 Original(LigCaretList<'a>),
96 Extended(LigCaretList2<'a>),
98}
99
100impl<'a> SelectedLigCaretList<'a> {
101 pub fn coverage(&self) -> Result<CoverageTable<'a>, ReadError> {
103 match self {
104 Self::Original(t) => t.coverage(),
105 Self::Extended(t) => t.coverage(),
106 }
107 }
108
109 pub fn lig_glyph_count(&self) -> u32 {
111 match self {
112 Self::Original(t) => u32::from(t.lig_glyph_count()),
113 Self::Extended(t) => t.lig_glyph_count().to_u32(),
114 }
115 }
116
117 pub fn lig_glyphs(&self) -> super::layout::LayoutOffsetArray<'a, LigGlyph<'a>> {
119 match self {
120 Self::Original(t) => super::layout::LayoutOffsetArray::Offset16(t.lig_glyphs()),
121 Self::Extended(t) => super::layout::LayoutOffsetArray::Offset24(t.lig_glyphs()),
122 }
123 }
124}
125
126impl<'a> Gdef<'a> {
127 pub fn lig_caret_list(&self) -> Option<Result<SelectedLigCaretList<'a>, ReadError>> {
130 let offset =
131 match self.select_offset(self.lig_caret_list_offset(), self.lig_caret_list2_offset()) {
132 Ok(offset) => offset,
133 Err(error) => return Some(Err(error)),
134 };
135 if offset.is_null() {
136 return None;
137 }
138 let data = self.offset_data();
139 Some(match offset {
140 HeaderOffset::Original(offset) => {
141 offset.resolve(data).map(SelectedLigCaretList::Original)
142 }
143 HeaderOffset::Extended(offset) => {
144 offset.resolve(data).map(SelectedLigCaretList::Extended)
145 }
146 })
147 }
148
149 pub fn original_lig_caret_list(&self) -> Option<Result<LigCaretList<'a>, ReadError>> {
151 self.lig_caret_list_offset().resolve(self.offset_data())
152 }
153}