1use super::hb_mask_t;
2use super::unicode::CharExt;
3use crate::hb::face::BasicFontMetrics;
4use crate::hb::glyph_metrics::GlyphMetrics;
5use crate::hb::glyph_names::GlyphNames;
6use crate::hb::set_digest::hb_set_digest_t;
7use crate::hb::tables::TableRanges;
8use crate::hb::unicode::Codepoint;
9use crate::U32Set;
10use crate::{script, BufferClusterLevel, BufferFlags, Direction, Language, Script, SerializeFlags};
11use alloc::{string::String, vec::Vec};
12use core::cmp::min;
13use core::convert::TryFrom;
14use read_fonts::types::{F2Dot14, GlyphId, GlyphId16};
15
16const CONTEXT_LENGTH: usize = 5;
17
18#[repr(C)]
22#[derive(Clone, Copy, Default, Debug, bytemuck::Pod, bytemuck::Zeroable)]
23pub struct GlyphPosition {
24 pub x_advance: i32,
27 pub y_advance: i32,
30 pub x_offset: i32,
33 pub y_offset: i32,
36 pub(crate) var: u32,
37}
38
39impl GlyphPosition {
40 #[inline]
41 pub(crate) fn attach_chain(&self) -> i16 {
42 let v: &[i16; 2] = bytemuck::cast_ref(&self.var);
45 v[0]
46 }
47
48 #[inline]
49 pub(crate) fn set_attach_chain(&mut self, n: i16) {
50 let v: &mut [i16; 2] = bytemuck::cast_mut(&mut self.var);
51 v[0] = n;
52 }
53
54 #[inline]
55 pub(crate) fn attach_type(&self) -> u8 {
56 let v: &[u8; 4] = bytemuck::cast_ref(&self.var);
59 v[2]
60 }
61
62 #[inline]
63 pub(crate) fn set_attach_type(&mut self, n: u8) {
64 let v: &mut [u8; 4] = bytemuck::cast_mut(&mut self.var);
65 v[2] = n;
66 }
67}
68
69#[repr(C)]
77#[derive(Clone, Copy, Default, Debug, bytemuck::Pod, bytemuck::Zeroable)]
78pub struct GlyphInfo {
79 pub glyph_id: u32,
86 pub(crate) mask: hb_mask_t,
87 pub cluster: u32,
91 pub(crate) vars: [u32; 2],
92}
93
94#[allow(dead_code)]
95pub(crate) struct buffer_var_shape {
96 pub(crate) width: u8,
97 pub(crate) var_index: u8,
98 pub(crate) index: u8,
99}
100
101impl buffer_var_shape {
102 #[inline]
103 pub fn start(&self) -> u8 {
104 (self.var_index - 1) * 4 + self.index * self.width
105 }
106
107 #[inline]
108 pub fn count(&self) -> u8 {
109 self.width
110 }
111
112 #[inline]
113 pub fn bits(&self) -> u8 {
114 let start = self.start();
115 let end = start + self.count();
116 debug_assert!(end <= 8);
117 ((1u16 << end) - (1u16 << start)) as u8
118 }
119}
120
121macro_rules! declare_buffer_var {
122 ($ty:ty, $var_index:expr, $index:expr, $var_name:ident, $getter:ident, $setter:ident) => {
123 #[allow(dead_code)]
124 pub(crate) const $var_name: buffer_var_shape = buffer_var_shape {
125 width: core::mem::size_of::<$ty>() as u8,
126 var_index: $var_index,
127 index: $index,
128 };
129
130 #[inline]
131 #[allow(dead_code)]
132 pub(crate) fn $getter(&self) -> $ty {
133 const LEN: usize = core::mem::size_of::<u32>() / core::mem::size_of::<$ty>();
134 let v: &[$ty; LEN] = bytemuck::cast_ref(&self.vars[$var_index - 1usize]);
135 v[$index]
136 }
137
138 #[inline]
139 #[allow(dead_code)]
140 pub(crate) fn $setter(&mut self, value: $ty) {
141 const LEN: usize = core::mem::size_of::<u32>() / core::mem::size_of::<$ty>();
142 let v: &mut [$ty; LEN] = bytemuck::cast_mut(&mut self.vars[$var_index - 1usize]);
143 v[$index] = value;
144 }
145 };
146}
147
148macro_rules! declare_buffer_var_alias {
149 ($alias_var:ident, $ty:ty, $var_name:ident, $getter:ident, $setter:ident) => {
150 #[allow(dead_code)]
151 pub(crate) const $var_name: buffer_var_shape = GlyphInfo::$alias_var;
152
153 #[inline]
154 pub(crate) fn $getter(&self) -> $ty {
155 const { assert!(GlyphInfo::$alias_var.width == core::mem::size_of::<$ty>() as u8) };
156 const LEN: usize = core::mem::size_of::<u32>() / core::mem::size_of::<$ty>();
157 let v: &[$ty; LEN] =
158 bytemuck::cast_ref(&self.vars[GlyphInfo::$alias_var.var_index as usize - 1usize]);
159 v[GlyphInfo::$alias_var.index as usize]
160 }
161
162 #[inline]
163 pub(crate) fn $setter(&mut self, value: $ty) {
164 const { assert!(GlyphInfo::$alias_var.width == core::mem::size_of::<$ty>() as u8) };
165 const LEN: usize = core::mem::size_of::<u32>() / core::mem::size_of::<$ty>();
166 let v: &mut [$ty; LEN] = bytemuck::cast_mut(
167 &mut self.vars[GlyphInfo::$alias_var.var_index as usize - 1usize],
168 );
169 v[GlyphInfo::$alias_var.index as usize] = value;
170 }
171 };
172}
173
174#[derive(Copy, Clone, PartialEq, Eq, Hash, Debug)]
176pub struct GlyphFlags(pub(crate) u32);
177
178impl GlyphFlags {
179 pub const UNSAFE_TO_BREAK: Self = Self(0x0000_0001);
190
191 pub const UNSAFE_TO_CONCAT: Self = Self(0x0000_0002);
223
224 pub const SAFE_TO_INSERT_TATWEEL: Self = Self(0x0000_0004);
229
230 pub const ALL: Self = Self(Self::DEFINED_BITS);
232
233 pub(crate) const DEFINED_BITS: u32 = 0x0000_0007; pub const fn from_bits_truncate(bits: u32) -> Self {
237 Self(bits & Self::DEFINED_BITS)
238 }
239
240 #[inline(always)]
242 pub const fn to_bits(self) -> u32 {
243 self.0
244 }
245
246 #[inline(always)]
251 pub const fn is_unsafe_to_break(self) -> bool {
252 self.intersects(Self::UNSAFE_TO_BREAK)
253 }
254
255 #[inline(always)]
260 pub const fn is_unsafe_to_concat(self) -> bool {
261 self.intersects(Self::UNSAFE_TO_CONCAT)
262 }
263
264 #[inline(always)]
269 pub const fn is_safe_to_insert_tatweel(self) -> bool {
270 self.intersects(Self::SAFE_TO_INSERT_TATWEEL)
271 }
272
273 #[inline(always)]
275 pub const fn contains(self, other: Self) -> bool {
276 (self.0 & other.0) == other.0
277 }
278
279 #[inline(always)]
281 pub const fn intersects(self, other: Self) -> bool {
282 (self.0 & other.0) != 0
283 }
284}
285
286impl core::ops::BitOr for GlyphFlags {
287 type Output = Self;
288
289 #[inline(always)]
290 fn bitor(self, rhs: Self) -> Self::Output {
291 Self(self.0 | rhs.0)
292 }
293}
294
295impl core::ops::BitOrAssign for GlyphFlags {
296 #[inline(always)]
297 fn bitor_assign(&mut self, rhs: Self) {
298 self.0 |= rhs.0;
299 }
300}
301
302impl core::ops::BitAnd for GlyphFlags {
303 type Output = Self;
304
305 #[inline(always)]
306 fn bitand(self, rhs: Self) -> Self::Output {
307 Self(self.0 & rhs.0)
308 }
309}
310
311impl core::ops::BitAndAssign for GlyphFlags {
312 #[inline(always)]
313 fn bitand_assign(&mut self, rhs: Self) {
314 self.0 &= rhs.0;
315 }
316}
317
318impl core::ops::Not for GlyphFlags {
319 type Output = Self;
320
321 #[inline(always)]
322 fn not(self) -> Self::Output {
323 Self(!self.0 & Self::DEFINED_BITS)
324 }
325}
326
327impl GlyphInfo {
328 #[inline(always)]
330 pub const fn flags(&self) -> GlyphFlags {
331 GlyphFlags(self.mask)
332 }
333
334 #[inline(always)]
345 pub fn unsafe_to_break(&self) -> bool {
346 self.flags().is_unsafe_to_break()
347 }
348
349 #[inline(always)]
381 pub fn unsafe_to_concat(&self) -> bool {
382 self.flags().is_unsafe_to_concat()
383 }
384
385 #[inline(always)]
390 pub fn safe_to_insert_tatweel(&self) -> bool {
391 self.flags().is_safe_to_insert_tatweel()
392 }
393
394 pub(crate) fn as_codepoint(&self) -> Codepoint {
395 self.glyph_id
396 }
397
398 #[inline]
399 pub(crate) fn as_glyph(&self) -> GlyphId {
400 GlyphId::new(self.glyph_id)
401 }
402
403 #[inline]
404 pub(crate) fn as_gid16(&self) -> Option<GlyphId16> {
405 let gid: u16 = self.glyph_id.try_into().ok()?;
406 Some(gid.into())
407 }
408
409 pub(crate) fn init_unicode_props(&mut self, scratch_flags: &mut hb_buffer_scratch_flags_t) {
410 let u = self.as_codepoint();
411 let gc = u.general_category();
412 let mut props = gc.0 as u16;
413
414 if u >= 0x80 {
415 if u.is_default_ignorable() {
416 props |= UnicodeProps::IGNORABLE.bits();
417 *scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_DEFAULT_IGNORABLES;
418
419 match u {
420 0x200C => props |= UnicodeProps::CF_ZWNJ.bits(),
421 0x200D => props |= UnicodeProps::CF_ZWJ.bits(),
422
423 0x180B..=0x180D | 0x180F => props |= UnicodeProps::HIDDEN.bits(),
431
432 0xE0020..=0xE007F => props |= UnicodeProps::HIDDEN.bits(),
435
436 0x034F => {
439 props |= UnicodeProps::HIDDEN.bits();
440 *scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_CGJ;
441 }
442
443 _ => {}
444 }
445 }
446
447 if gc.is_mark() {
448 *scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_CONTINUATIONS;
449 props |= UnicodeProps::CONTINUATION.bits();
450 props |= (u.modified_combining_class() as u16) << 8;
451 }
452 }
453
454 self.set_unicode_props(props);
455 }
456
457 #[inline]
458 pub(crate) fn unhide(&mut self) {
459 let mut n = self.unicode_props();
460 n &= !UnicodeProps::HIDDEN.bits();
461 self.set_unicode_props(n);
462 }
463}
464
465pub type hb_buffer_cluster_level_t = u32;
466pub const HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES: u32 = 0;
467pub const HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS: u32 = 1;
468pub const HB_BUFFER_CLUSTER_LEVEL_CHARACTERS: u32 = 2;
469pub const HB_BUFFER_CLUSTER_LEVEL_GRAPHEMES: u32 = 3;
470pub const HB_BUFFER_CLUSTER_LEVEL_DEFAULT: u32 = HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES;
471
472pub struct hb_buffer_t {
473 pub flags: BufferFlags,
475 pub cluster_level: hb_buffer_cluster_level_t,
476 pub invisible: Option<GlyphId>,
477 pub not_found_variation_selector: Option<u32>,
478
479 pub direction: Direction,
481 pub script: Option<Script>,
482 pub language: Option<Language>,
483
484 pub successful: bool,
486 pub(crate) have_output: bool,
488 pub have_separate_output: bool,
489 pub have_positions: bool,
491
492 pub idx: usize,
493 pub len: usize,
494 pub out_len: usize,
495
496 pub info: Vec<GlyphInfo>,
497 pub pos: Vec<GlyphPosition>,
498
499 pub context: [[Codepoint; CONTEXT_LENGTH]; 2],
503 pub context_len: [usize; 2],
504
505 pub(crate) digest: hb_set_digest_t,
506 pub(crate) glyph_set: U32Set,
507
508 pub allocated_var_bits: u8,
510 pub serial: u8,
511 pub scratch_flags: hb_buffer_scratch_flags_t,
512 pub max_len: usize,
514 pub max_ops: i32,
516}
517
518impl hb_buffer_t {
519 pub const MAX_LEN_FACTOR: usize = 256;
520 pub const MAX_LEN_MIN: usize = 65536;
521 pub const MAX_LEN_DEFAULT: usize = 0x3FFF_FFFF;
523
524 pub const MAX_OPS_FACTOR: i32 = 4096;
525 pub const MAX_OPS_MIN: i32 = 65536;
526 pub const MAX_OPS_DEFAULT: i32 = 0x1FFF_FFFF;
528
529 pub fn new() -> Self {
531 hb_buffer_t {
532 flags: BufferFlags::empty(),
533 cluster_level: HB_BUFFER_CLUSTER_LEVEL_DEFAULT,
534 invisible: None,
535 scratch_flags: HB_BUFFER_SCRATCH_FLAG_DEFAULT,
536 not_found_variation_selector: None,
537 max_len: Self::MAX_LEN_DEFAULT,
538 max_ops: Self::MAX_OPS_DEFAULT,
539 direction: Direction::Invalid,
540 script: None,
541 language: None,
542 successful: true,
543 have_output: false,
544 have_positions: false,
545 idx: 0,
546 len: 0,
547 out_len: 0,
548 info: Vec::new(),
549 pos: Vec::new(),
550 have_separate_output: false,
551 allocated_var_bits: 0,
552 serial: 0,
553 context: Default::default(),
554 context_len: [0, 0],
555 digest: hb_set_digest_t::new(),
556 glyph_set: U32Set::default(),
557 }
558 }
559
560 #[inline]
561 pub fn allocate_var(&mut self, shape: buffer_var_shape) {
562 let bits = shape.bits();
563 debug_assert_eq!(
564 self.allocated_var_bits & bits,
565 0,
566 "Variable already allocated"
567 );
568 self.allocated_var_bits |= bits;
569 }
570
571 #[inline]
572 pub fn try_allocate_var(&mut self, shape: buffer_var_shape) -> bool {
573 let bits = shape.bits();
574 if self.allocated_var_bits & bits != 0 {
575 return false;
576 }
577 self.allocated_var_bits |= bits;
578 true
579 }
580
581 #[inline]
582 pub fn deallocate_var(&mut self, shape: buffer_var_shape) {
583 let bits = shape.bits();
584 debug_assert_eq!(
585 self.allocated_var_bits & bits,
586 bits,
587 "Deallocating unallocated var"
588 );
589 self.allocated_var_bits &= !bits;
590 }
591
592 #[inline]
593 pub fn assert_var(&self, shape: buffer_var_shape) {
594 let bits = shape.bits();
595 debug_assert_eq!(
596 self.allocated_var_bits & bits,
597 bits,
598 "Variable not allocated"
599 );
600 }
601
602 #[inline]
603 pub fn info_slice_mut(&mut self) -> &mut [GlyphInfo] {
604 &mut self.info[..self.len]
605 }
606
607 #[inline]
608 pub fn out_info(&self) -> &[GlyphInfo] {
609 if self.have_separate_output {
610 bytemuck::cast_slice(self.pos.as_slice())
611 } else {
612 &self.info
613 }
614 }
615
616 #[inline]
617 pub fn out_info_mut(&mut self) -> &mut [GlyphInfo] {
618 if self.have_separate_output {
619 bytemuck::cast_slice_mut(self.pos.as_mut_slice())
620 } else {
621 &mut self.info
622 }
623 }
624
625 #[inline]
626 fn set_out_info(&mut self, i: usize, info: GlyphInfo) {
627 self.out_info_mut()[i] = info;
628 }
629
630 #[inline]
631 pub fn cur(&self, i: usize) -> &GlyphInfo {
632 &self.info[self.idx + i]
633 }
634
635 #[inline]
636 pub fn cur_mut(&mut self, i: usize) -> &mut GlyphInfo {
637 let idx = self.idx + i;
638 &mut self.info[idx]
639 }
640
641 #[inline]
642 pub fn cur_pos_mut(&mut self) -> &mut GlyphPosition {
643 let i = self.idx;
644 &mut self.pos[i]
645 }
646
647 #[inline]
648 pub fn prev(&self) -> &GlyphInfo {
649 let idx = self.out_len.saturating_sub(1);
650 &self.out_info()[idx]
651 }
652
653 #[inline]
654 pub fn prev_mut(&mut self) -> &mut GlyphInfo {
655 let idx = self.out_len.saturating_sub(1);
656 &mut self.out_info_mut()[idx]
657 }
658
659 pub fn update_digest(&mut self) {
660 self.digest = hb_set_digest_t::new();
661 self.digest.add_array(self.info.iter().map(|i| i.glyph_id));
662 }
663 pub fn update_glyph_set(&mut self) {
664 self.glyph_set.clear();
665 self.glyph_set
666 .extend_unsorted(self.info.iter().map(|i| i.glyph_id));
667 }
668
669 fn clear(&mut self) {
670 self.direction = Direction::Invalid;
671 self.script = None;
672 self.language = None;
673
674 self.successful = true;
675 self.have_output = false;
676 self.have_positions = false;
677
678 self.idx = 0;
679 self.info.clear();
680 self.pos.clear();
681 self.len = 0;
682 self.out_len = 0;
683 self.have_separate_output = false;
684
685 self.context = Default::default();
686 self.context_len = [0, 0];
687
688 self.serial = 0;
689 self.scratch_flags = HB_BUFFER_SCRATCH_FLAG_DEFAULT;
690 self.cluster_level = HB_BUFFER_CLUSTER_LEVEL_DEFAULT;
691 self.not_found_variation_selector = None;
692 }
693
694 #[inline]
695 pub fn backtrack_len(&self) -> usize {
696 if self.have_output {
697 self.out_len
698 } else {
699 self.idx
700 }
701 }
702
703 #[inline]
704 pub fn lookahead_len(&self) -> usize {
705 self.len - self.idx
706 }
707
708 #[inline]
709 fn next_serial(&mut self) -> u8 {
710 self.serial = self.serial.wrapping_add(1);
712
713 if self.serial == 0 {
714 self.serial += 1;
715 }
716
717 self.serial
718 }
719
720 fn add(&mut self, codepoint: u32, cluster: u32) {
721 if !self.ensure(self.len + 1) {
722 return;
723 }
724 self.info[self.len] = GlyphInfo {
725 glyph_id: codepoint,
726 cluster,
727 ..GlyphInfo::default()
728 };
729 self.len += 1;
730 }
731
732 #[inline]
733 pub fn reverse(&mut self) {
734 if self.is_empty() {
735 return;
736 }
737
738 self.reverse_range(0, self.len);
739 }
740
741 pub fn reverse_range(&mut self, start: usize, end: usize) {
742 if end - start < 2 {
743 return;
744 }
745
746 self.info[start..end].reverse();
747 if self.have_positions {
748 self.pos[start..end].reverse();
749 }
750 }
751
752 pub fn reverse_groups<F>(&mut self, group: F, merge_clusters: bool)
753 where
754 F: Fn(&GlyphInfo, &GlyphInfo) -> bool,
755 {
756 if self.is_empty() {
757 return;
758 }
759
760 let mut start = 0;
761 let mut i = 1;
762
763 while i < self.len {
764 if !group(&self.info[i - 1], &self.info[i]) {
765 if merge_clusters {
766 self.merge_clusters(start, i);
767 }
768
769 self.reverse_range(start, i);
770 start = i;
771 }
772
773 i += 1;
774 }
775
776 if merge_clusters {
777 self.merge_clusters(start, i);
778 }
779
780 self.reverse_range(start, i);
781
782 self.reverse();
783 }
784
785 pub fn group_end<F>(&self, mut start: usize, group: F) -> usize
786 where
787 F: Fn(&GlyphInfo, &GlyphInfo) -> bool,
788 {
789 start += 1;
790
791 while start < self.len && group(&self.info[start - 1], &self.info[start]) {
792 start += 1;
793 }
794
795 start
796 }
797
798 #[inline]
799 fn reset_clusters(&mut self) {
800 for (i, info) in self.info.iter_mut().enumerate() {
801 info.cluster = i as u32;
802 }
803 }
804
805 pub fn guess_segment_properties(&mut self) {
806 if self.script.is_none() {
807 for info in &self.info {
808 match info.as_codepoint().script() {
809 script::COMMON | script::INHERITED | script::UNKNOWN => {}
810 s => {
811 self.script = Some(s);
812 break;
813 }
814 }
815 }
816 }
817
818 if self.direction == Direction::Invalid {
819 if let Some(script) = self.script {
820 self.direction = Direction::from_script(script).unwrap_or_default();
821 }
822
823 if self.direction == Direction::Invalid {
824 self.direction = Direction::LeftToRight;
825 }
826 }
827
828 }
830
831 pub fn sync(&mut self) -> bool {
832 debug_assert!(self.have_output);
833 debug_assert!(self.idx <= self.len);
834
835 if !self.successful {
836 self.have_output = false;
837 self.out_len = 0;
838 self.idx = 0;
839 return false;
840 }
841
842 self.next_glyphs(self.len - self.idx);
843
844 if self.have_separate_output {
845 let info: Vec<GlyphPosition> = bytemuck::cast_vec(core::mem::take(&mut self.info));
847 let pos: Vec<GlyphInfo> = bytemuck::cast_vec(core::mem::take(&mut self.pos));
848 self.pos = info;
849 self.info = pos;
850 self.have_separate_output = false;
851 }
852
853 self.len = self.out_len;
854
855 self.have_output = false;
856 self.out_len = 0;
857 self.idx = 0;
858 true
859 }
860
861 pub fn clear_output(&mut self) {
862 self.have_output = true;
863 self.have_positions = false;
864
865 self.idx = 0;
866 self.out_len = 0;
867 self.have_separate_output = false;
868 }
869
870 pub fn clear_positions(&mut self) {
871 self.have_output = false;
872 self.have_positions = true;
873
874 self.out_len = 0;
875 self.have_separate_output = false;
876
877 for pos in &mut self.pos {
878 *pos = GlyphPosition::default();
879 }
880 }
881
882 pub fn replace_glyphs(&mut self, num_in: usize, num_out: usize, glyph_data: &[u32]) {
883 if !self.make_room_for(num_in, num_out) {
884 return;
885 }
886
887 debug_assert!(self.idx + num_in <= self.len);
888
889 self.merge_clusters(self.idx, self.idx + num_in);
890
891 let orig_info = self.info[self.idx];
892 for i in 0..num_out {
893 let ii = self.out_len + i;
894 self.set_out_info(ii, orig_info);
895 self.out_info_mut()[ii].glyph_id = glyph_data[i];
896 }
897
898 self.idx += num_in;
899 self.out_len += num_out;
900 }
901
902 pub fn replace_glyph(&mut self, glyph_index: u32) {
903 if self.have_separate_output || self.out_len != self.idx {
904 if !self.make_room_for(1, 1) {
905 return;
906 }
907
908 self.set_out_info(self.out_len, self.info[self.idx]);
909 }
910
911 let out_len = self.out_len;
912 self.out_info_mut()[out_len].glyph_id = glyph_index;
913
914 self.idx += 1;
915 self.out_len += 1;
916 }
917
918 pub fn output_glyph(&mut self, glyph_index: u32) {
919 if !self.make_room_for(0, 1) {
920 return;
921 }
922
923 if self.idx == self.len && self.out_len == 0 {
924 return;
925 }
926
927 let out_len = self.out_len;
928 if self.idx < self.len {
929 self.set_out_info(out_len, self.info[self.idx]);
930 } else {
931 let info = self.out_info()[out_len - 1];
932 self.set_out_info(out_len, info);
933 }
934
935 self.out_info_mut()[out_len].glyph_id = glyph_index;
936
937 self.out_len += 1;
938 }
939
940 pub fn output_info(&mut self, glyph_info: GlyphInfo) {
941 if !self.make_room_for(0, 1) {
942 return;
943 }
944
945 self.set_out_info(self.out_len, glyph_info);
946 self.out_len += 1;
947 }
948
949 pub fn copy_glyph(&mut self) {
951 if !self.make_room_for(0, 1) {
952 return;
953 }
954
955 self.set_out_info(self.out_len, self.info[self.idx]);
956 self.out_len += 1;
957 }
958
959 #[inline(always)]
963 pub fn next_glyph(&mut self) {
964 if self.have_output {
965 if self.have_separate_output || self.out_len != self.idx {
966 if !self.ensure(self.out_len + 1) {
967 return;
968 }
969
970 let i = self.out_len;
971 self.out_info_mut()[i] = self.info[self.idx];
972 }
973
974 self.out_len += 1;
975 }
976
977 self.idx += 1;
978 }
979
980 pub fn next_glyphs(&mut self, n: usize) {
984 if self.have_output {
985 if self.have_separate_output || self.out_len != self.idx {
986 if !self.ensure(self.out_len + n) {
987 return;
988 }
989
990 for i in 0..n {
991 self.set_out_info(self.out_len + i, self.info[self.idx + i]);
992 }
993 }
994
995 self.out_len += n;
996 }
997
998 self.idx += n;
999 }
1000
1001 pub fn skip_glyph(&mut self) {
1003 self.idx += 1;
1004 }
1005
1006 pub fn reset_masks(&mut self, mask: hb_mask_t) {
1007 for info in &mut self.info[..self.len] {
1008 info.mask = mask;
1009 }
1010 }
1011
1012 pub fn set_masks(
1013 &mut self,
1014 mut value: hb_mask_t,
1015 mask: hb_mask_t,
1016 cluster_start: u32,
1017 cluster_end: u32,
1018 ) {
1019 if mask == 0 {
1020 return;
1021 }
1022
1023 let not_mask = !mask;
1024 value &= mask;
1025
1026 self.max_ops -= self.len as i32;
1027 if self.max_ops < 0 {
1028 self.successful = false;
1029 }
1030
1031 if cluster_start == 0 && cluster_end == u32::MAX {
1032 for info in &mut self.info[..self.len] {
1033 info.mask = (info.mask & not_mask) | value;
1034 }
1035
1036 return;
1037 }
1038
1039 for info in &mut self.info[..self.len] {
1040 if cluster_start <= info.cluster && info.cluster < cluster_end {
1041 info.mask = (info.mask & not_mask) | value;
1042 }
1043 }
1044 }
1045
1046 #[inline(always)]
1047 pub fn merge_clusters(&mut self, start: usize, end: usize) {
1048 if end - start < 2 {
1049 return;
1050 }
1051
1052 if !BufferClusterLevel::new(self.cluster_level).is_monotone() {
1053 self.unsafe_to_break(Some(start), Some(end));
1054 return;
1055 }
1056
1057 self.merge_clusters_impl(start, end);
1058 }
1059
1060 fn merge_clusters_impl(&mut self, mut start: usize, mut end: usize) {
1061 self.max_ops -= (end - start) as i32;
1062 if self.max_ops < 0 {
1063 self.successful = false;
1064 }
1065
1066 let cluster = self.info[start..end]
1067 .iter()
1068 .map(|info| info.cluster)
1069 .min()
1070 .unwrap();
1071
1072 if cluster != self.info[end - 1].cluster {
1074 while end < self.len && self.info[end - 1].cluster == self.info[end].cluster {
1075 end += 1;
1076 }
1077 }
1078
1079 if cluster != self.info[start].cluster {
1081 while self.idx < start && self.info[start - 1].cluster == self.info[start].cluster {
1082 start -= 1;
1083 }
1084 }
1085
1086 if self.idx == start && self.info[start].cluster != cluster {
1088 let mut i = self.out_len;
1089 while i != 0 && self.out_info()[i - 1].cluster == self.info[start].cluster {
1090 Self::set_cluster(&mut self.out_info_mut()[i - 1], cluster, 0);
1091 i -= 1;
1092 }
1093 }
1094
1095 for info in &mut self.info[start..end] {
1096 Self::set_cluster(info, cluster, 0);
1097 }
1098 }
1099
1100 pub fn merge_grapheme_clusters(&mut self, start: usize, end: usize) {
1101 if end - start < 2 {
1102 return;
1103 }
1104
1105 if !BufferClusterLevel::new(self.cluster_level).is_graphemes() {
1106 self.unsafe_to_break(Some(start), Some(end));
1107 return;
1108 }
1109
1110 self.merge_clusters_impl(start, end);
1111 }
1112
1113 pub fn merge_out_clusters(&mut self, start: usize, end: usize) {
1114 if end - start < 2 {
1115 return;
1116 }
1117
1118 if !BufferClusterLevel::new(self.cluster_level).is_monotone() {
1119 return;
1120 }
1121
1122 self.merge_out_clusters_impl(start, end);
1123 }
1124
1125 pub fn merge_out_grapheme_clusters(&mut self, start: usize, end: usize) {
1126 if end - start < 2 {
1127 return;
1128 }
1129
1130 if !BufferClusterLevel::new(self.cluster_level).is_graphemes() {
1131 return;
1132 }
1133
1134 self.merge_out_clusters_impl(start, end);
1135 }
1136
1137 fn merge_out_clusters_impl(&mut self, mut start: usize, mut end: usize) {
1138 self.max_ops -= (end - start) as i32;
1139 if self.max_ops < 0 {
1140 self.successful = false;
1141 }
1142
1143 let cluster = self.out_info()[start..end]
1144 .iter()
1145 .map(|info| info.cluster)
1146 .min()
1147 .unwrap();
1148
1149 while start != 0 && self.out_info()[start - 1].cluster == self.out_info()[start].cluster {
1151 start -= 1;
1152 }
1153
1154 while end < self.out_len && self.out_info()[end - 1].cluster == self.out_info()[end].cluster
1156 {
1157 end += 1;
1158 }
1159
1160 if end == self.out_len {
1162 let mut i = self.idx;
1163 while i < self.len && self.info[i].cluster == self.out_info()[end - 1].cluster {
1164 Self::set_cluster(&mut self.info[i], cluster, 0);
1165 i += 1;
1166 }
1167 }
1168
1169 for info in &mut self.out_info_mut()[start..end] {
1170 Self::set_cluster(info, cluster, 0);
1171 }
1172 }
1173
1174 pub fn delete_glyph(&mut self) {
1176 let cluster = self.info[self.idx].cluster;
1177
1178 if (self.idx + 1 < self.len && cluster == self.info[self.idx + 1].cluster)
1179 || (self.out_len != 0 && cluster == self.out_info()[self.out_len - 1].cluster)
1180 {
1181 self.skip_glyph();
1183 return;
1184 }
1185
1186 if self.out_len != 0 {
1187 if cluster < self.out_info()[self.out_len - 1].cluster {
1189 let mask = self.info[self.idx].mask;
1190 let old_cluster = self.out_info()[self.out_len - 1].cluster;
1191
1192 let mut i = self.out_len;
1193 while i != 0 && self.out_info()[i - 1].cluster == old_cluster {
1194 Self::set_cluster(&mut self.out_info_mut()[i - 1], cluster, mask);
1195 i -= 1;
1196 }
1197 }
1198
1199 self.skip_glyph();
1200 return;
1201 }
1202
1203 if self.idx + 1 < self.len {
1204 self.merge_clusters(self.idx, self.idx + 2);
1206 }
1207
1208 self.skip_glyph();
1209 }
1210
1211 pub fn delete_glyphs_inplace(&mut self, filter: impl Fn(&GlyphInfo) -> bool) {
1212 let mut j = 0;
1215
1216 for i in 0..self.len {
1217 if filter(&self.info[i]) {
1218 let cluster = self.info[i].cluster;
1222 if i + 1 < self.len && cluster == self.info[i + 1].cluster {
1223 continue;
1225 }
1226
1227 if j != 0 {
1228 if cluster < self.info[j - 1].cluster {
1230 let mask = self.info[i].mask;
1231 let old_cluster = self.info[j - 1].cluster;
1232
1233 let mut k = j;
1234 while k > 0 && self.info[k - 1].cluster == old_cluster {
1235 Self::set_cluster(&mut self.info[k - 1], cluster, mask);
1236 k -= 1;
1237 }
1238 }
1239 continue;
1240 }
1241
1242 if i + 1 < self.len {
1243 self.merge_clusters(i, i + 2);
1245 }
1246
1247 continue;
1248 }
1249
1250 if j != i {
1251 self.info[j] = self.info[i];
1252 self.pos[j] = self.pos[i];
1253 }
1254
1255 j += 1;
1256 }
1257
1258 self.len = j;
1259 }
1260
1261 pub fn unsafe_to_break(&mut self, start: Option<usize>, end: Option<usize>) {
1262 self.set_glyph_flags(
1263 GlyphFlags::UNSAFE_TO_BREAK | GlyphFlags::UNSAFE_TO_CONCAT,
1264 start,
1265 end,
1266 Some(true),
1267 None,
1268 );
1269 }
1270
1271 pub fn safe_to_insert_tatweel(&mut self, start: Option<usize>, end: Option<usize>) {
1272 if !self
1273 .flags
1274 .contains(BufferFlags::PRODUCE_SAFE_TO_INSERT_TATWEEL)
1275 {
1276 self.unsafe_to_break(start, end);
1277 return;
1278 }
1279
1280 self.set_glyph_flags(
1281 GlyphFlags::SAFE_TO_INSERT_TATWEEL,
1282 start,
1283 end,
1284 Some(true),
1285 None,
1286 );
1287 }
1288
1289 fn _set_glyph_flags_impl(
1290 &mut self,
1291 mask: hb_mask_t,
1292 start: usize,
1293 end: usize,
1294 interior: bool,
1295 from_out_buffer: bool,
1296 ) {
1297 if !from_out_buffer || !self.have_output {
1298 if !interior {
1299 for info in &mut self.info[start..end] {
1300 info.mask |= mask;
1301 }
1302 } else {
1303 let cluster = self._infos_find_min_cluster(&self.info, start, end, None);
1304 self._infos_set_glyph_flags(false, start, end, cluster, mask);
1305 }
1306 } else {
1307 debug_assert!(start <= self.out_len);
1308 debug_assert!(self.idx <= end);
1309
1310 if !interior {
1311 let range_end = self.out_len;
1312 for info in &mut self.out_info_mut()[start..range_end] {
1313 info.mask |= mask;
1314 }
1315
1316 for info in &mut self.info[self.idx..end] {
1317 info.mask |= mask;
1318 }
1319 } else {
1320 let mut cluster = self._infos_find_min_cluster(&self.info, self.idx, end, None);
1321 cluster = self._infos_find_min_cluster(
1322 self.out_info(),
1323 start,
1324 self.out_len,
1325 Some(cluster),
1326 );
1327
1328 let out_len = self.out_len;
1329 self._infos_set_glyph_flags(true, start, out_len, cluster, mask);
1330 self._infos_set_glyph_flags(false, self.idx, end, cluster, mask);
1331 }
1332 }
1333 }
1334
1335 fn set_glyph_flags(
1339 &mut self,
1340 flags: GlyphFlags,
1341 start: Option<usize>,
1342 end: Option<usize>,
1343 interior: Option<bool>,
1344 from_out_buffer: Option<bool>,
1345 ) {
1346 if let (Some(start), Some(end)) = (start, end) {
1349 if end.wrapping_sub(start) > 255 {
1350 return;
1351 }
1352 }
1353
1354 let start = start.unwrap_or(0);
1355 let end = min(end.unwrap_or(self.len), self.len);
1356 let interior = interior.unwrap_or(false);
1357 let from_out_buffer = from_out_buffer.unwrap_or(false);
1358
1359 if interior && !from_out_buffer && end - start < 2 {
1360 return;
1361 }
1362
1363 self._set_glyph_flags_impl(flags.0, start, end, interior, from_out_buffer);
1364 }
1365
1366 pub fn unsafe_to_concat(&mut self, start: Option<usize>, end: Option<usize>) {
1367 if !self.flags.contains(BufferFlags::PRODUCE_UNSAFE_TO_CONCAT) {
1368 return;
1369 }
1370
1371 self.set_glyph_flags(GlyphFlags::UNSAFE_TO_CONCAT, start, end, Some(false), None);
1372 }
1373
1374 pub fn unsafe_to_break_from_outbuffer(&mut self, start: Option<usize>, end: Option<usize>) {
1375 self.set_glyph_flags(
1376 GlyphFlags::UNSAFE_TO_BREAK | GlyphFlags::UNSAFE_TO_CONCAT,
1377 start,
1378 end,
1379 Some(true),
1380 Some(true),
1381 );
1382 }
1383
1384 pub fn unsafe_to_concat_from_outbuffer(&mut self, start: Option<usize>, end: Option<usize>) {
1385 if !self.flags.contains(BufferFlags::PRODUCE_UNSAFE_TO_CONCAT) {
1386 return;
1387 }
1388
1389 self.set_glyph_flags(
1390 GlyphFlags::UNSAFE_TO_CONCAT,
1391 start,
1392 end,
1393 Some(false),
1394 Some(true),
1395 );
1396 }
1397
1398 pub fn move_to(&mut self, i: usize) -> bool {
1399 if !self.have_output {
1400 debug_assert!(i <= self.len);
1401 self.idx = i;
1402 return true;
1403 }
1404
1405 if !self.successful {
1406 return false;
1407 }
1408
1409 debug_assert!(i <= self.out_len + (self.len - self.idx));
1410
1411 if self.out_len < i {
1412 let count = i - self.out_len;
1413 if !self.make_room_for(count, count) {
1414 return false;
1415 }
1416
1417 for j in 0..count {
1418 self.set_out_info(self.out_len + j, self.info[self.idx + j]);
1419 }
1420
1421 self.idx += count;
1422 self.out_len += count;
1423 } else if self.out_len > i {
1424 let count = self.out_len - i;
1426
1427 if self.idx < count && !self.shift_forward(count - self.idx) {
1435 return false;
1436 }
1437
1438 debug_assert!(self.idx >= count);
1439
1440 self.idx -= count;
1441 self.out_len -= count;
1442
1443 for j in 0..count {
1444 self.info[self.idx + j] = self.out_info()[self.out_len + j];
1445 }
1446 }
1447
1448 true
1449 }
1450
1451 #[must_use]
1452 #[inline(always)]
1453 pub fn ensure(&mut self, size: usize) -> bool {
1454 if size <= self.info.len() {
1455 true
1456 } else {
1457 self.enlarge(size)
1458 }
1459 }
1460
1461 #[must_use]
1462 fn enlarge(&mut self, size: usize) -> bool {
1463 if size > self.max_len {
1464 self.successful = false;
1465 return false;
1466 }
1467
1468 self.info.resize(size, GlyphInfo::default());
1469 self.pos.resize(size, GlyphPosition::default());
1470 true
1471 }
1472
1473 #[must_use]
1474 fn make_room_for(&mut self, num_in: usize, num_out: usize) -> bool {
1475 if !self.ensure(self.out_len + num_out) {
1476 return false;
1477 }
1478
1479 if !self.have_separate_output && self.out_len + num_out > self.idx + num_in {
1480 debug_assert!(self.have_output);
1481
1482 self.have_separate_output = true;
1483 for i in 0..self.out_len {
1484 self.set_out_info(i, self.info[i]);
1485 }
1486 }
1487
1488 true
1489 }
1490
1491 fn shift_forward(&mut self, count: usize) -> bool {
1492 debug_assert!(self.have_output);
1493 if !self.ensure(self.len + count) {
1494 return false;
1495 }
1496
1497 self.max_ops -= (self.len - self.idx) as i32;
1498 if self.max_ops < 0 {
1499 self.successful = false;
1500 return false;
1501 }
1502
1503 for i in (0..(self.len - self.idx)).rev() {
1504 self.info[self.idx + count + i] = self.info[self.idx + i];
1505 }
1506
1507 if self.idx + count > self.len {
1508 for info in &mut self.info[self.len..self.idx + count] {
1509 *info = GlyphInfo::default();
1510 }
1511 }
1512
1513 self.len += count;
1514 self.idx += count;
1515
1516 true
1517 }
1518
1519 fn clear_context(&mut self, side: usize) {
1520 self.context_len[side] = 0;
1521 }
1522
1523 pub fn sort(&mut self, start: usize, end: usize, cmp: impl Fn(&GlyphInfo, &GlyphInfo) -> bool) {
1524 debug_assert!(!self.have_positions);
1525
1526 for i in start + 1..end {
1527 let mut j = i;
1528 while j > start && cmp(&self.info[j - 1], &self.info[i]) {
1529 j -= 1;
1530 }
1531
1532 if i == j {
1533 continue;
1534 }
1535
1536 self.merge_clusters(j, i + 1);
1538
1539 {
1540 let t = self.info[i];
1541 for idx in (0..i - j).rev() {
1542 self.info[idx + j + 1] = self.info[idx + j];
1543 }
1544
1545 self.info[j] = t;
1546 }
1547 }
1548 }
1549
1550 pub fn set_cluster(info: &mut GlyphInfo, cluster: u32, mask: hb_mask_t) {
1551 if info.cluster != cluster {
1552 info.mask = (info.mask & !GlyphFlags::DEFINED_BITS) | (mask & GlyphFlags::DEFINED_BITS);
1553 }
1554
1555 info.cluster = cluster;
1556 }
1557
1558 pub(crate) fn enter(&mut self) {
1560 self.serial = 0;
1561 self.scratch_flags = HB_BUFFER_SCRATCH_FLAG_DEFAULT;
1562
1563 if let Some(len) = self.len.checked_mul(hb_buffer_t::MAX_LEN_FACTOR) {
1564 self.max_len = len.max(hb_buffer_t::MAX_LEN_MIN);
1565 }
1566
1567 if let Ok(len) = i32::try_from(self.len) {
1568 if let Some(ops) = len.checked_mul(hb_buffer_t::MAX_OPS_FACTOR) {
1569 self.max_ops = ops.max(hb_buffer_t::MAX_OPS_MIN);
1570 }
1571 }
1572 }
1573
1574 pub(crate) fn leave(&mut self) {
1576 self.max_len = hb_buffer_t::MAX_LEN_DEFAULT;
1577 self.max_ops = hb_buffer_t::MAX_OPS_DEFAULT;
1578 self.serial = 0;
1579 }
1580
1581 fn _infos_find_min_cluster(
1582 &self,
1583 info: &[GlyphInfo],
1584 start: usize,
1585 end: usize,
1586 cluster: Option<u32>,
1587 ) -> u32 {
1588 let mut cluster = cluster.unwrap_or(u32::MAX);
1589
1590 if start == end {
1591 return cluster;
1592 }
1593
1594 if self.cluster_level == HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS {
1595 for glyph_info in &info[start..end] {
1596 cluster = min(cluster, glyph_info.cluster);
1597 }
1598 }
1599
1600 cluster.min(info[start].cluster.min(info[end - 1].cluster))
1601 }
1602
1603 #[inline(always)]
1604 fn _infos_set_glyph_flags(
1605 &mut self,
1606 out_info: bool,
1607 start: usize,
1608 end: usize,
1609 cluster: u32,
1610 mask: hb_mask_t,
1611 ) {
1612 if start == end {
1613 return;
1614 }
1615
1616 let cluster_level = self.cluster_level;
1617
1618 let infos = if out_info {
1619 self.out_info_mut()
1620 } else {
1621 self.info.as_mut_slice()
1622 };
1623
1624 let cluster_first = infos[start].cluster;
1625 let cluster_last = infos[end - 1].cluster;
1626
1627 if cluster_level == HB_BUFFER_CLUSTER_LEVEL_CHARACTERS
1628 || (cluster != cluster_first && cluster != cluster_last)
1629 {
1630 for info in &mut infos[start..end] {
1631 if info.cluster != cluster {
1632 info.mask |= mask;
1633 }
1634 }
1635
1636 return;
1637 }
1638
1639 if cluster == cluster_first {
1641 let mut i = end;
1642 while start < i && infos[i - 1].cluster != cluster_first {
1643 if cluster != infos[i - 1].cluster {
1644 infos[i - 1].mask |= mask;
1645 }
1646
1647 i -= 1;
1648 }
1649 } else {
1650 let mut i = start;
1651 while i < end && infos[i].cluster != cluster_last {
1652 if cluster != infos[i].cluster {
1653 infos[i].mask |= mask;
1654 }
1655
1656 i += 1;
1657 }
1658 }
1659 }
1660
1661 pub fn is_empty(&self) -> bool {
1663 self.len == 0
1664 }
1665
1666 fn push_str(&mut self, text: &str) {
1667 if !self.ensure(self.len + text.chars().count()) {
1668 return;
1669 }
1670
1671 for (i, c) in text.char_indices() {
1672 self.info[self.len] = GlyphInfo {
1673 glyph_id: c as u32,
1674 cluster: i as u32,
1675 ..GlyphInfo::default()
1676 };
1677 self.len += 1;
1678 }
1679 }
1680
1681 fn set_pre_context(&mut self, text: &str) {
1682 self.clear_context(0);
1683 for (i, c) in text.chars().rev().enumerate().take(CONTEXT_LENGTH) {
1684 self.context[0][i] = c as Codepoint;
1685 self.context_len[0] += 1;
1686 }
1687 }
1688
1689 fn set_pre_context_codepoints(&mut self, codepoints: &[u32]) {
1690 self.clear_context(0);
1691 for (i, &c) in codepoints.iter().take(CONTEXT_LENGTH).enumerate() {
1692 self.context[0][i] = c;
1693 self.context_len[0] += 1;
1694 }
1695 }
1696
1697 fn set_post_context(&mut self, text: &str) {
1698 self.clear_context(1);
1699 for (i, c) in text.chars().enumerate().take(CONTEXT_LENGTH) {
1700 self.context[1][i] = c as Codepoint;
1701 self.context_len[1] += 1;
1702 }
1703 }
1704
1705 fn set_post_context_codepoints(&mut self, codepoints: &[u32]) {
1706 self.clear_context(1);
1707 for (i, &c) in codepoints.iter().take(CONTEXT_LENGTH).enumerate() {
1708 self.context[1][i] = c;
1709 self.context_len[1] += 1;
1710 }
1711 }
1712
1713 pub fn next_syllable(&self, mut start: usize) -> usize {
1714 if start >= self.len {
1715 return start;
1716 }
1717
1718 let syllable = self.info[start].syllable();
1719 start += 1;
1720 while start < self.len && syllable == self.info[start].syllable() {
1721 start += 1;
1722 }
1723
1724 start
1725 }
1726
1727 #[inline]
1728 pub fn allocate_lig_id(&mut self) -> u8 {
1729 let mut lig_id = self.next_serial() & 0x07;
1730
1731 if lig_id == 0 {
1732 lig_id = self.allocate_lig_id();
1733 }
1734
1735 lig_id
1736 }
1737}
1738
1739pub(crate) fn _cluster_group_func(a: &GlyphInfo, b: &GlyphInfo) -> bool {
1740 a.cluster == b.cluster
1741}
1742
1743macro_rules! foreach_cluster {
1746 ($buffer:expr, $start:ident, $end:ident, $($body:tt)*) => {
1747 foreach_group!($buffer, $start, $end, $crate::hb::buffer::_cluster_group_func, $($body)*)
1748 };
1749}
1750
1751macro_rules! foreach_group {
1752 ($buffer:expr, $start:ident, $end:ident, $group_func:expr, $($body:tt)*) => {{
1753 let count = $buffer.len;
1754 let mut $start = 0;
1755 let mut $end = if count > 0 { $buffer.group_end(0, $group_func) } else { 0 };
1756
1757 while $start < count {
1758 $($body)*;
1759 $start = $end;
1760 $end = $buffer.group_end($start, $group_func);
1761 }
1762 }};
1763}
1764
1765macro_rules! foreach_syllable {
1766 ($buffer:expr, $start:ident, $end:ident, $($body:tt)*) => {{
1767 let mut $start = 0;
1768 let mut $end = $buffer.next_syllable(0);
1769 while $start < $buffer.len {
1770 $($body)*;
1771 $start = $end;
1772 $end = $buffer.next_syllable($start);
1773 }
1774 }};
1775}
1776
1777macro_rules! foreach_grapheme {
1778 ($buffer:expr, $start:ident, $end:ident, $($body:tt)*) => {
1779 foreach_group!($buffer, $start, $end, $crate::hb::ot_layout::_hb_grapheme_group_func, $($body)*)
1780 };
1781}
1782
1783bitflags::bitflags! {
1784 #[derive(Default, Debug, Clone, Copy)]
1785 pub struct UnicodeProps: u16 {
1786 const GENERAL_CATEGORY = 0x001F;
1787 const IGNORABLE = 0x0020;
1788 const HIDDEN = 0x0040;
1790 const CONTINUATION = 0x0080;
1791
1792 const CF_ZWJ = 0x0100;
1794 const CF_ZWNJ = 0x0200;
1795 const CF_VS = 0x0400;
1796 const CF_AAT_DELETED = 0x0800;
1797 }
1798}
1799
1800bitflags::bitflags! {
1801 #[derive(Default, Debug, Clone, Copy)]
1802 pub struct GlyphPropsFlags: u16 {
1803 const BASE_GLYPH = 0x02;
1805 const LIGATURE = 0x04;
1806 const MARK = 0x08;
1807 const CLASS_MASK = Self::BASE_GLYPH.bits() | Self::LIGATURE.bits() | Self::MARK.bits();
1808
1809 const SUBSTITUTED = 0x10;
1811 const LIGATED = 0x20;
1812 const MULTIPLIED = 0x40;
1813
1814 const PRESERVE = Self::SUBSTITUTED.bits() | Self::LIGATED.bits() | Self::MULTIPLIED.bits();
1815 }
1816}
1817
1818pub type hb_buffer_scratch_flags_t = u32;
1819pub const HB_BUFFER_SCRATCH_FLAG_DEFAULT: u32 = 0x0000_0000;
1820pub const HB_BUFFER_SCRATCH_FLAG_HAS_FRACTION_SLASH: u32 = 0x0000_0001;
1821pub const HB_BUFFER_SCRATCH_FLAG_HAS_DEFAULT_IGNORABLES: u32 = 0x0000_0002;
1822pub const HB_BUFFER_SCRATCH_FLAG_HAS_SPACE_FALLBACK: u32 = 0x0000_0004;
1823pub const HB_BUFFER_SCRATCH_FLAG_HAS_GPOS_ATTACHMENT: u32 = 0x0000_0008;
1824pub const HB_BUFFER_SCRATCH_FLAG_HAS_CGJ: u32 = 0x0000_0010;
1825pub const HB_BUFFER_SCRATCH_FLAG_HAS_BROKEN_SYLLABLE: u32 = 0x0000_0020;
1826pub const HB_BUFFER_SCRATCH_FLAG_HAS_VARIATION_SELECTOR_FALLBACK: u32 = 0x0000_0040;
1827pub const HB_BUFFER_SCRATCH_FLAG_HAS_CONTINUATIONS: u32 = 0x0000_0080;
1828
1829pub const HB_BUFFER_SCRATCH_FLAG_SHAPER0: u32 = 0x0100_0000;
1831pub struct UnicodeBuffer(pub(crate) hb_buffer_t);
1837
1838impl UnicodeBuffer {
1839 #[inline]
1841 pub fn new() -> UnicodeBuffer {
1842 UnicodeBuffer(hb_buffer_t::new())
1843 }
1844
1845 #[inline]
1850 pub fn len(&self) -> usize {
1851 self.0.len
1852 }
1853
1854 pub fn reserve(&mut self, size: usize) -> bool {
1856 self.0.ensure(size)
1857 }
1858
1859 #[inline]
1861 pub fn is_empty(&self) -> bool {
1862 self.0.is_empty()
1863 }
1864
1865 #[inline]
1867 pub fn push_str(&mut self, str: &str) {
1868 self.0.push_str(str);
1869 }
1870
1871 #[inline]
1873 pub fn set_pre_context(&mut self, str: &str) {
1874 self.0.set_pre_context(str);
1875 }
1876
1877 #[inline]
1883 pub fn set_pre_context_codepoints(&mut self, codepoints: &[u32]) {
1884 self.0.set_pre_context_codepoints(codepoints);
1885 }
1886
1887 #[inline]
1889 pub fn set_post_context(&mut self, str: &str) {
1890 self.0.set_post_context(str);
1891 }
1892
1893 #[inline]
1895 pub fn set_post_context_codepoints(&mut self, codepoints: &[u32]) {
1896 self.0.set_post_context_codepoints(codepoints);
1897 }
1898
1899 #[inline]
1901 pub fn push_glyph_infos(&mut self, infos: &[GlyphInfo]) -> bool {
1902 let len = infos.len();
1903 if !self.0.ensure(self.0.len + len) {
1904 return false;
1905 }
1906
1907 self.0.info[self.0.len..self.0.len + len].copy_from_slice(infos);
1908 self.0.len += len;
1909 true
1910 }
1911
1912 #[inline]
1914 pub fn add(&mut self, codepoint: char, cluster: u32) {
1915 self.0.add(codepoint as u32, cluster);
1916 self.0.context_len[1] = 0;
1917 }
1918
1919 #[inline]
1921 pub fn set_direction(&mut self, direction: Direction) {
1922 self.0.direction = direction;
1923 }
1924
1925 #[inline]
1927 pub fn direction(&self) -> Direction {
1928 self.0.direction
1929 }
1930
1931 #[inline]
1933 pub fn set_script(&mut self, script: Script) {
1934 self.0.script = Some(script);
1935 }
1936
1937 pub fn script(&self) -> Script {
1939 self.0.script.unwrap_or(script::UNKNOWN)
1940 }
1941
1942 #[inline]
1944 pub fn set_language(&mut self, lang: Language) {
1945 self.0.language = Some(lang);
1946 }
1947
1948 #[inline]
1950 pub fn set_not_found_variation_selector_glyph(&mut self, glyph: u32) {
1951 self.0.not_found_variation_selector = Some(glyph);
1952 }
1953
1954 #[inline]
1956 pub fn language(&self) -> Option<Language> {
1957 self.0.language.clone()
1958 }
1959
1960 #[inline]
1963 pub fn guess_segment_properties(&mut self) {
1964 self.0.guess_segment_properties();
1965 }
1966
1967 #[inline]
1969 pub fn set_flags(&mut self, flags: BufferFlags) {
1970 self.0.flags = flags;
1971 }
1972
1973 #[inline]
1975 pub fn flags(&self) -> BufferFlags {
1976 self.0.flags
1977 }
1978
1979 #[inline]
1981 pub fn set_cluster_level(&mut self, cluster_level: BufferClusterLevel) {
1982 self.0.cluster_level = match cluster_level {
1983 BufferClusterLevel::MonotoneGraphemes => HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES,
1984 BufferClusterLevel::MonotoneCharacters => HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS,
1985 BufferClusterLevel::Characters => HB_BUFFER_CLUSTER_LEVEL_CHARACTERS,
1986 BufferClusterLevel::Graphemes => HB_BUFFER_CLUSTER_LEVEL_GRAPHEMES,
1987 }
1988 }
1989
1990 #[inline]
1992 pub fn cluster_level(&self) -> BufferClusterLevel {
1993 match self.0.cluster_level {
1994 HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES => BufferClusterLevel::MonotoneGraphemes,
1995 HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS => BufferClusterLevel::MonotoneCharacters,
1996 HB_BUFFER_CLUSTER_LEVEL_CHARACTERS => BufferClusterLevel::Characters,
1997 HB_BUFFER_CLUSTER_LEVEL_GRAPHEMES => BufferClusterLevel::Graphemes,
1998 _ => BufferClusterLevel::MonotoneGraphemes,
1999 }
2000 }
2001
2002 #[inline]
2004 pub fn reset_clusters(&mut self) {
2005 self.0.reset_clusters();
2006 }
2007
2008 #[inline]
2010 pub fn clear(&mut self) {
2011 self.0.clear();
2012 }
2013}
2014
2015impl core::fmt::Debug for UnicodeBuffer {
2016 fn fmt(&self, fmt: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
2017 fmt.debug_struct("UnicodeBuffer")
2018 .field("direction", &self.direction())
2019 .field("language", &self.language())
2020 .field("script", &self.script())
2021 .field("cluster_level", &self.cluster_level())
2022 .finish()
2023 }
2024}
2025
2026impl Default for UnicodeBuffer {
2027 fn default() -> UnicodeBuffer {
2028 UnicodeBuffer::new()
2029 }
2030}
2031
2032pub struct GlyphBuffer(pub(crate) hb_buffer_t);
2034
2035impl GlyphBuffer {
2036 #[inline]
2042 pub fn len(&self) -> usize {
2043 self.0.len
2044 }
2045
2046 #[inline]
2048 pub fn is_empty(&self) -> bool {
2049 self.0.is_empty()
2050 }
2051
2052 #[inline]
2054 pub fn glyph_infos(&self) -> &[GlyphInfo] {
2055 &self.0.info[0..self.0.len]
2056 }
2057
2058 #[inline]
2060 pub fn glyph_positions(&self) -> &[GlyphPosition] {
2061 &self.0.pos[0..self.0.len]
2062 }
2063
2064 #[inline]
2067 pub fn clear(mut self) -> UnicodeBuffer {
2068 self.0.clear();
2069 UnicodeBuffer(self.0)
2070 }
2071
2072 pub fn serialize(&self, font: &impl SerializerFont, flags: SerializeFlags) -> String {
2074 self.serialize_impl(font, flags).unwrap_or_default()
2075 }
2076
2077 pub(crate) fn serialize_impl(
2078 &self,
2079 font: &impl SerializerFont,
2080 flags: SerializeFlags,
2081 ) -> Result<String, core::fmt::Error> {
2082 use core::fmt::Write;
2083
2084 let mut s = String::with_capacity(64);
2085
2086 let info = self.glyph_infos();
2087 let pos = self.glyph_positions();
2088 let mut x = 0;
2089 let mut y = 0;
2090 let names = font.glyph_names();
2091 let glyph_metrics = if flags.contains(SerializeFlags::GLYPH_EXTENTS) {
2092 Some(font.glyph_metrics())
2093 } else {
2094 None
2095 };
2096 for (info, pos) in info.iter().zip(pos) {
2097 s.push(if s.is_empty() { '[' } else { '|' });
2098
2099 if !flags.contains(SerializeFlags::NO_GLYPH_NAMES) {
2100 match names.get(info.as_glyph().to_u32()) {
2101 Some(name) => s.push_str(name),
2102 None => write!(&mut s, "gid{}", info.glyph_id)?,
2103 }
2104 } else {
2105 write!(&mut s, "{}", info.glyph_id)?;
2106 }
2107
2108 if !flags.contains(SerializeFlags::NO_CLUSTERS) {
2109 write!(&mut s, "={}", info.cluster)?;
2110 }
2111
2112 if !flags.contains(SerializeFlags::NO_POSITIONS) {
2113 if x + pos.x_offset != 0 || y + pos.y_offset != 0 {
2114 write!(&mut s, "@{},{}", x + pos.x_offset, y + pos.y_offset)?;
2115 }
2116
2117 if !flags.contains(SerializeFlags::NO_ADVANCES) {
2118 write!(&mut s, "+{}", pos.x_advance)?;
2119 if pos.y_advance != 0 {
2120 write!(&mut s, ",{}", pos.y_advance)?;
2121 }
2122 }
2123 }
2124
2125 if flags.contains(SerializeFlags::GLYPH_FLAGS) {
2126 if info.mask & GlyphFlags::DEFINED_BITS != 0 {
2127 write!(&mut s, "#{:X}", info.mask & GlyphFlags::DEFINED_BITS)?;
2128 }
2129 }
2130
2131 if flags.contains(SerializeFlags::GLYPH_EXTENTS) {
2132 let extents = glyph_metrics
2133 .as_ref()
2134 .unwrap()
2135 .extents(info.as_glyph(), font.coords())
2136 .unwrap_or_default();
2137 write!(
2138 &mut s,
2139 "<{},{},{},{}>",
2140 extents.x_bearing, extents.y_bearing, extents.width, extents.height
2141 )?;
2142 }
2143
2144 if flags.contains(SerializeFlags::NO_ADVANCES) {
2145 x += pos.x_advance;
2146 y += pos.y_advance;
2147 }
2148 }
2149
2150 if !s.is_empty() {
2151 s.push(']');
2152 }
2153
2154 Ok(s)
2155 }
2156}
2157
2158pub trait SerializerFont {
2159 fn coords(&self) -> &[F2Dot14];
2160 fn glyph_names(&self) -> GlyphNames<'_>;
2161 fn glyph_metrics(&self) -> GlyphMetrics<'_>;
2162}
2163
2164impl SerializerFont for crate::Shaper<'_> {
2165 fn coords(&self) -> &[F2Dot14] {
2166 self.coords()
2167 }
2168
2169 fn glyph_names(&self) -> GlyphNames<'_> {
2170 crate::Shaper::glyph_names(self)
2171 }
2172
2173 fn glyph_metrics(&self) -> GlyphMetrics<'_> {
2174 crate::Shaper::glyph_metrics(self)
2175 }
2176}
2177
2178impl SerializerFont for crate::font::FontInstance {
2179 fn coords(&self) -> &[F2Dot14] {
2180 self.normalized_coords()
2181 }
2182
2183 fn glyph_names(&self) -> GlyphNames<'_> {
2184 GlyphNames::from_tables(&self.tables())
2185 }
2186
2187 fn glyph_metrics(&self) -> GlyphMetrics<'_> {
2188 let table_ranges = TableRanges::from_tables(&self.tables());
2189 let metrics = BasicFontMetrics {
2190 num_glyphs: table_ranges.num_glyphs,
2191 units_per_em: table_ranges.units_per_em,
2192 ascent: table_ranges.ascent,
2193 descent: table_ranges.descent,
2194 };
2195 GlyphMetrics::from_tables(&self.tables(), &metrics)
2196 }
2197}
2198
2199impl core::fmt::Debug for GlyphBuffer {
2200 fn fmt(&self, fmt: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
2201 fmt.debug_struct("GlyphBuffer")
2202 .field("glyph_positions", &self.glyph_positions())
2203 .field("glyph_infos", &self.glyph_infos())
2204 .finish()
2205 }
2206}