rustybuzz/hb/ot/layout/GSUB/
ligature.rs

1use crate::hb::ot_layout_gsubgpos::OT::hb_ot_apply_context_t;
2use crate::hb::ot_layout_gsubgpos::{
3    ligate_input, match_glyph, match_input, Apply, WouldApply, WouldApplyContext,
4};
5use ttf_parser::gsub::Ligature;
6
7impl WouldApply for Ligature<'_> {
8    fn would_apply(&self, ctx: &WouldApplyContext) -> bool {
9        ctx.glyphs.len() == usize::from(self.components.len()) + 1
10            && self
11                .components
12                .into_iter()
13                .enumerate()
14                .all(|(i, comp)| ctx.glyphs[i + 1] == comp)
15    }
16}
17
18impl Apply for Ligature<'_> {
19    fn apply(&self, ctx: &mut hb_ot_apply_context_t) -> Option<()> {
20        // Special-case to make it in-place and not consider this
21        // as a "ligated" substitution.
22        if self.components.is_empty() {
23            ctx.replace_glyph(self.glyph);
24            Some(())
25        } else {
26            let f = |glyph, index| {
27                let value = self.components.get(index).unwrap();
28                match_glyph(glyph, value.0)
29            };
30
31            let mut match_end = 0;
32            let mut match_positions = smallvec::SmallVec::from_elem(0, 4);
33            let mut total_component_count = 0;
34
35            if !match_input(
36                ctx,
37                self.components.len(),
38                &f,
39                &mut match_end,
40                &mut match_positions,
41                Some(&mut total_component_count),
42            ) {
43                ctx.buffer
44                    .unsafe_to_concat(Some(ctx.buffer.idx), Some(match_end));
45                return None;
46            }
47
48            let count = usize::from(self.components.len()) + 1;
49            ligate_input(
50                ctx,
51                count,
52                &match_positions,
53                match_end,
54                total_component_count,
55                self.glyph,
56            );
57            Some(())
58        }
59    }
60}