1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
use crate::{Tag, NormalizedCoordinate};
use crate::parser::{Stream, FromData, Offset, Offset16, LazyArray16};
use crate::var_store::ItemVariationStore;
#[derive(Clone, Copy)]
struct ValueRecord {
value_tag: Tag,
delta_set_outer_index: u16,
delta_set_inner_index: u16,
}
impl FromData for ValueRecord {
const SIZE: usize = 8;
#[inline]
fn parse(data: &[u8]) -> Option<Self> {
let mut s = Stream::new(data);
Some(ValueRecord {
value_tag: s.read::<Tag>()?,
delta_set_outer_index: s.read::<u16>()?,
delta_set_inner_index: s.read::<u16>()?,
})
}
}
#[derive(Clone, Copy)]
pub struct Table<'a> {
variation_store: ItemVariationStore<'a>,
records: LazyArray16<'a, ValueRecord>,
}
impl<'a> Table<'a> {
pub fn parse(data: &'a [u8]) -> Option<Self> {
let mut s = Stream::new(data);
let version = s.read::<u32>()?;
if version != 0x00010000 {
return None;
}
s.skip::<u16>();
let value_record_size = s.read::<u16>()?;
if usize::from(value_record_size) != ValueRecord::SIZE {
return None;
}
let count = s.read::<u16>()?;
if count == 0 {
return None;
}
let var_store_offset = s.read::<Option<Offset16>>()??.to_usize();
let records = s.read_array16::<ValueRecord>(count)?;
let variation_store = ItemVariationStore::parse(Stream::new_at(data, var_store_offset)?)?;
Some(Table {
variation_store,
records,
})
}
pub fn metric_offset(&self, tag: Tag, coordinates: &[NormalizedCoordinate]) -> Option<f32> {
let (_, record) = self.records.binary_search_by(|r| r.value_tag.cmp(&tag))?;
self.variation_store.parse_delta(
record.delta_set_outer_index,
record.delta_set_inner_index,
coordinates
)
}
}
impl core::fmt::Debug for Table<'_> {
fn fmt(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
write!(f, "Table {{ ... }}")
}
}