1use std::{
2 cmp::Ordering,
3 fmt::Display,
4 ops::{Bound, RangeBounds},
5 sync::Arc,
6};
7
8use append_only_bytes::AppendOnlyBytes;
9
10use fxhash::FxHashMap;
11use generic_btree::{
12 rle::{HasLength, Mergeable, Sliceable},
13 BTree, MoveEvent, QueryResult,
14};
15use smallvec::SmallVec;
16
17use crate::{
18 rich_text::{ann::insert_anchors_at_same_elem, op::OpContent, rich_tree::utf16::get_utf16_len},
19 Anchor, AnchorType, Annotation, ClientID, Counter, IdSpan, OpID, Style,
20};
21
22use self::{
23 ann::{insert_anchor_to_char, AnchorSetDiff, AnnIdx, AnnManager, Span, StyleCalculator},
24 cursor::CursorMap,
25 encoding::{decode, encode},
26 op::{Op, OpStore},
27 rich_tree::{
28 query::{IndexFinder, IndexType},
29 rich_tree_btree_impl::RichTreeTrait,
30 CacheDiff, Elem,
31 },
32 vv::VersionVector,
33};
34
35mod ann;
36mod cursor;
37mod encoding;
38mod id_map;
39mod iter;
40mod op;
41mod rich_tree;
42#[cfg(test)]
43mod test;
44#[cfg(feature = "test")]
45pub mod test_utils;
46pub mod vv;
47
48pub struct RichText {
49 bytes: AppendOnlyBytes,
50 content: BTree<RichTreeTrait>,
51 cursor_map: CursorMap,
52 store: OpStore,
53 pending_ops: Vec<Op>,
54 ann: AnnManager,
55 init_styles: StyleCalculator,
58}
59
60impl RichText {
61 pub fn new(client_id: u64) -> Self {
62 let cursor_map: CursorMap = Default::default();
63 let update_fn = cursor_map.gen_update_fn();
64 let mut content: BTree<RichTreeTrait> = BTree::new();
65 content.set_listener(Some(update_fn));
66 RichText {
67 bytes: AppendOnlyBytes::new(),
68 content,
69 cursor_map,
70 store: OpStore::new(client_id),
71 pending_ops: Default::default(),
72 ann: AnnManager::new(),
73 init_styles: StyleCalculator::default(),
74 }
75 }
76
77 #[inline]
78 fn next_id(&self) -> OpID {
79 self.store.next_id()
80 }
81
82 #[inline]
83 pub fn insert_utf16(&mut self, index: usize, string: &str) {
84 self.insert_inner(index, string, IndexType::Utf16);
85 }
86
87 #[inline]
88 pub fn insert(&mut self, index: usize, string: &str) {
89 self.insert_inner(index, string, IndexType::Utf8);
90 }
91
92 fn insert_inner(&mut self, index: usize, string: &str, index_type: IndexType) {
93 if string.is_empty() {
94 return;
95 }
96
97 fn can_merge_new_slice(
98 elem: &Elem,
99 id: OpID,
100 right: Option<OpID>,
101 slice: &append_only_bytes::BytesSlice,
102 ) -> bool {
103 elem.id.client == id.client
104 && elem.id.counter + elem.atom_len() as Counter == id.counter
105 && elem.right == right
106 && !elem.is_dead()
107 && elem.string.can_merge(slice)
108 && !elem.has_after_anchor()
109 }
110
111 let start = self.bytes.len();
112 self.bytes.push_str(string);
113 let slice = self.bytes.slice(start..);
114 let cache_diff = Some(CacheDiff::new_len_diff(
115 string.len() as isize,
116 get_utf16_len(&slice) as isize,
117 ));
118 let id = self.next_id();
119 if index == 0 {
120 let first_leaf = self.content.first_leaf();
121 let right_origin = self
122 .content
123 .get_node(first_leaf)
124 .elements()
125 .first()
126 .map(|x| x.id);
127 self.store
128 .insert_local(OpContent::new_insert(None, right_origin, slice.clone()));
129 self.content
130 .prepend(Elem::new(id, None, right_origin, slice));
131 return;
132 }
133
134 let path = self.find_ideal_insert_pos(index, index_type);
136 let left;
137 let right;
138 let op_slice = slice.clone();
139 {
140 let mut node = self.content.get_node(path.leaf);
142 let offset = path.offset;
143 let index = path.elem_index;
144 if offset != 0 {
145 left = Some(node.elements()[index].id.inc((offset - 1) as u32));
146 } else {
147 left = Some(node.elements()[index - 1].id_last());
148 }
149 if offset < node.elements()[index].rle_len() {
150 right = Some(node.elements()[index].id.inc(offset as u32));
151 } else if index + 1 < node.elements().len() {
152 right = Some(node.elements()[index + 1].id);
153 } else if let Some(next) = self.content.next_same_level_node(path.leaf) {
154 node = self.content.get_node(next);
155 right = Some(node.elements()[0].id);
156 } else {
157 right = None;
158 }
159 }
160
161 self.content.update_leaf(path.leaf, |elements| {
162 debug_assert!(path.elem_index < elements.len());
164 let mut offset = path.offset;
165 let mut index = path.elem_index;
166 if offset == 0 {
167 assert!(index > 0);
169 index -= 1;
170 offset = elements[index].rle_len();
171 }
172
173 if offset == elements[index].rle_len() {
174 if can_merge_new_slice(&elements[index], id, right, &slice) {
175 elements[index].merge_slice(&slice);
177 self.cursor_map
178 .update(MoveEvent::new_move(path.leaf, &elements[index]));
179 return (true, cache_diff);
180 }
181
182 elements.insert(index + 1, Elem::new(id, left, right, slice));
183 self.cursor_map
184 .update(MoveEvent::new_move(path.leaf, &elements[index + 1]));
185 return (true, cache_diff);
186 }
187
188 let right_half = elements[index].split(offset);
190 elements.splice(
191 index + 1..index + 1,
192 [Elem::new(id, left, right, slice), right_half],
193 );
194 self.cursor_map
195 .update(MoveEvent::new_move(path.leaf, &elements[index + 1]));
196 (true, cache_diff)
197 });
198
199 self.store
200 .insert_local(OpContent::new_insert(left, right, op_slice));
201 }
202
203 fn find_ideal_insert_pos(&mut self, index: usize, index_type: IndexType) -> QueryResult {
224 let mut path = self.content.query::<IndexFinder>(&(index, index_type));
225 loop {
226 let node = self.content.get_node(path.leaf);
227
228 while path.offset == 0 && path.elem_index > 0 {
230 path.elem_index -= 1;
231 path.offset = node.elements()[path.elem_index].rle_len();
232 if node.elements()[path.elem_index].has_after_anchor() {
233 break;
234 }
235 }
236
237 while path.elem_index > 0
239 && node.elements()[path.elem_index].is_dead()
240 && !node.elements()[path.elem_index].has_after_anchor()
241 {
242 path.elem_index -= 1;
243 path.offset = node.elements()[path.elem_index].rle_len();
244 }
245
246 if path.offset == 0 && path.elem_index == 0 {
247 while path.offset == 0 && path.elem_index == 0 {
249 match self.content.prev_same_level_node(path.leaf) {
250 Some(prev) => {
251 let node = self.content.get_node(prev);
252 path.elem_index = node.len();
253 path.offset = 0;
254 path.leaf = prev;
255 }
256 None => unreachable!(), }
258 }
259 } else {
260 break;
261 }
262 }
263 path
264 }
265
266 pub fn delete_utf16(&mut self, range: impl RangeBounds<usize>) {
267 self.delete_inner(range, IndexType::Utf16);
268 }
269
270 pub fn delete(&mut self, range: impl RangeBounds<usize>) {
271 self.delete_inner(range, IndexType::Utf8);
272 }
273
274 fn delete_inner(&mut self, range: impl RangeBounds<usize>, index_type: IndexType) {
275 let start = match range.start_bound() {
276 Bound::Included(start) => *start,
277 Bound::Excluded(start) => *start + 1,
278 Bound::Unbounded => 0,
279 };
280 let end = match range.end_bound() {
281 Bound::Included(end) => *end + 1,
282 Bound::Excluded(end) => *end,
283 Bound::Unbounded => self.len(),
284 };
285
286 if start == end {
287 return;
288 }
289
290 let start_result = self.content.query::<IndexFinder>(&(start, index_type));
291 let end_result = self.content.query::<IndexFinder>(&(end, index_type));
292 let mut deleted = SmallVec::<[(OpID, usize); 4]>::new();
293
294 let mut delete_fn = |elem: &mut Elem| {
296 if elem.local_delete() {
297 deleted.push((elem.id, elem.rle_len()));
298 (-(elem.rle_len() as isize), -(elem.utf16_len as isize))
299 } else {
300 (0, 0)
301 }
302 };
303 self.content.update_with_filter(
304 &start_result..&end_result,
305 &mut |slice| {
306 match (slice.start, slice.end) {
307 (Some((start_idx, start_offset)), Some((end_idx, end_offset)))
308 if start_idx == end_idx =>
309 {
310 if start_idx >= slice.elements.len() {
312 return (false, None);
313 }
314
315 let elem = &mut slice.elements[start_idx];
316 if elem.is_dead() {
317 return (false, None);
318 }
319
320 let (additions, diff) =
321 elem.update(start_offset, end_offset, &mut delete_fn);
322 let (len_diff, utf16_len_diff) = diff.unwrap();
323 if !additions.is_empty() {
324 let len = additions.len();
325 slice
326 .elements
327 .splice(start_idx + 1..start_idx + 1, additions);
328 Elem::try_merge_arr(slice.elements, start_idx, len + 1);
329 } else if start_idx > 0 {
330 Elem::try_merge_arr(slice.elements, start_idx - 1, 2);
331 } else {
332 Elem::try_merge_arr(slice.elements, start_idx, 1);
333 }
334
335 return (
336 true,
337 Some(CacheDiff::new_len_diff(len_diff, utf16_len_diff)),
338 );
339 }
340 _ => {}
341 }
342
343 let mut len_diff = 0;
344 let mut utf16_len_diff = 0;
345 let mut end = match slice.end {
346 Some((end_idx, end_offset)) => {
347 if end_offset == 0 {
348 end_idx
349 } else {
350 let elem = &mut slice.elements[end_idx];
351 if !elem.is_dead() {
352 let (additions, diff) = elem.update(0, end_offset, &mut delete_fn);
353 if !additions.is_empty() {
354 slice.elements.splice(end_idx + 1..end_idx + 1, additions);
355 }
356 len_diff += diff.unwrap().0;
357 utf16_len_diff += diff.unwrap().1;
358 }
359 end_idx + 1
360 }
361 }
362 None => slice.elements.len(),
363 };
364
365 let start = match slice.start {
366 Some((start_idx, start_offset)) => {
367 if start_offset == 0 {
368 start_idx
369 } else {
370 let elem = &mut slice.elements[start_idx];
371 if !elem.is_dead() && start_offset < elem.rle_len() {
372 let (additions, diff) =
373 elem.update(start_offset, elem.rle_len(), &mut delete_fn);
374 if !additions.is_empty() {
375 end += additions.len();
376 slice
377 .elements
378 .splice(start_idx + 1..start_idx + 1, additions);
379 }
380 len_diff += diff.unwrap().0;
381 utf16_len_diff += diff.unwrap().1;
382 }
383 start_idx + 1
384 }
385 }
386 None => 0,
387 };
388
389 for elem in slice.elements[start..end].iter_mut() {
390 let diff = delete_fn(elem);
391 len_diff += diff.0;
392 utf16_len_diff += diff.1;
393 }
394
395 let begin = start.saturating_sub(2);
396 Elem::try_merge_arr(slice.elements, begin, end + 2 - begin);
397 (
398 true,
399 Some(CacheDiff::new_len_diff(len_diff, utf16_len_diff)),
400 )
401 },
402 &|cache| cache.len > 0,
403 );
404
405 for (start, len) in deleted {
406 let op = self
407 .store
408 .insert_local(OpContent::new_delete(start, len as i32));
409 }
411 }
412
413 pub fn annotate_utf16(&mut self, range: impl RangeBounds<usize>, style: Style) {
421 self.annotate_inner(range, style, IndexType::Utf16)
422 }
423
424 pub fn annotate(&mut self, range: impl RangeBounds<usize>, style: Style) {
432 self.annotate_inner(range, style, IndexType::Utf8)
433 }
434
435 fn annotate_inner(
436 &mut self,
437 range: impl RangeBounds<usize>,
438 style: Style,
439 index_type: IndexType,
440 ) {
441 let start = match range.start_bound() {
442 Bound::Included(start) => *start,
443 Bound::Excluded(start) => *start + 1,
444 Bound::Unbounded => 0,
445 };
446 let mut inclusive_end = match range.end_bound() {
447 Bound::Included(end) => *end,
448 Bound::Excluded(end) => *end - 1,
449 Bound::Unbounded => self.len_with(index_type) - 1,
450 };
451
452 if inclusive_end < start {
453 return;
454 }
455
456 inclusive_end = inclusive_end.min(self.len_with(index_type) - 1);
457 let start = if style.start_type == AnchorType::Before {
458 Some(self.content.query::<IndexFinder>(&(start, index_type)))
459 } else if start == 0 {
460 None
461 } else {
462 Some(
463 self.content
464 .query::<IndexFinder>(&(start.saturating_sub(1), index_type)),
465 )
466 };
467 let inclusive_end = if style.end_type == AnchorType::Before {
468 if inclusive_end + 1 >= self.len_with(index_type) {
469 None
470 } else {
471 Some(
472 self.content
473 .query::<IndexFinder>(&(inclusive_end + 1, index_type)),
474 )
475 }
476 } else {
477 Some(
478 self.content
479 .query::<IndexFinder>(&(inclusive_end, index_type)),
480 )
481 };
482
483 let start_id = start.map(|start| self.get_id_at_pos(start));
484 let end_id = inclusive_end.map(|end| self.get_id_at_pos(end));
485 let id = self.next_id();
486 let lamport = self.next_lamport();
487 let ann = Annotation {
488 id,
489 range_lamport: (lamport, id),
490 range: crate::AnchorRange {
491 start: Anchor {
492 id: start_id,
493 type_: style.start_type,
494 },
495 end: Anchor {
496 id: end_id,
497 type_: style.end_type,
498 },
499 },
500 behavior: style.behavior,
501 type_: style.type_.clone(),
502 meta: None,
503 };
504
505 let ann = Arc::new(ann);
506 let ann_idx = self.ann.register(ann.clone());
507
508 match (start, inclusive_end) {
510 (Some(start), Some(end)) => {
511 self.annotate_given_range(start, end, ann_idx, style);
512 }
513 (Some(start), None) => {
514 self.content.update_leaf(start.leaf, |elements| {
515 ann::insert_anchor_to_char(
516 elements,
517 start.elem_index,
518 start.offset,
519 ann_idx,
520 style.start_type,
521 true,
522 );
523 (true, Some(AnchorSetDiff::from_ann(ann_idx, true).into()))
524 });
525 }
528 (None, Some(end)) => {
529 self.content.update_leaf(end.leaf, |elements| {
530 ann::insert_anchor_to_char(
531 elements,
532 end.elem_index,
533 end.offset,
534 ann_idx,
535 style.end_type,
536 false,
537 );
538 (true, Some(AnchorSetDiff::from_ann(ann_idx, false).into()))
539 });
540 self.init_styles.insert_start(ann_idx);
541 }
542 (None, None) => {
543 self.init_styles.insert_start(ann_idx);
544 }
546 }
547
548 let op = self.store.insert_local(OpContent::new_ann(ann));
550 }
552
553 fn annotate_given_range(
554 &mut self,
555 start: QueryResult,
556 end: QueryResult,
557 ann_idx: AnnIdx,
558 style: Style,
559 ) {
560 self.content
561 .update2_leaf(start.leaf, end.leaf, |elements, from| {
562 match from {
563 Some(leaf) => {
564 if leaf == end.leaf {
565 ann::insert_anchor_to_char(
567 elements,
568 end.elem_index,
569 end.offset,
570 ann_idx,
571 style.end_type,
572 false,
573 );
574 } else {
575 debug_assert_eq!(leaf, start.leaf);
577 ann::insert_anchor_to_char(
578 elements,
579 start.elem_index,
580 start.offset,
581 ann_idx,
582 style.start_type,
583 true,
584 );
585 }
586
587 true
588 }
589 None => {
590 if start.elem_index == end.elem_index {
591 assert_ne!(end.offset, elements[start.elem_index].rle_len());
592 let new = insert_anchors_at_same_elem(
593 &mut elements[start.elem_index],
594 start.offset,
595 end.offset,
596 ann_idx,
597 style.start_type,
598 style.end_type,
599 );
600
601 elements.splice(start.elem_index + 1..start.elem_index + 1, new);
602 return true;
603 }
604
605 assert!(end.elem_index > start.elem_index);
606 ann::insert_anchor_to_char(
607 elements,
608 end.elem_index,
609 end.offset,
610 ann_idx,
611 style.end_type,
612 false,
613 );
614 ann::insert_anchor_to_char(
615 elements,
616 start.elem_index,
617 start.offset,
618 ann_idx,
619 style.start_type,
620 true,
621 );
622
623 true
624 }
625 }
626 })
627 }
628
629 fn get_id_at_pos(&self, pos: QueryResult) -> OpID {
630 let node = self.content.get_node(pos.leaf);
631 let elem = &node.elements()[pos.elem_index];
633 assert!(pos.offset < elem.rle_len());
634 elem.id.inc(pos.offset as u32)
635 }
636
637 pub fn iter(&self) -> impl Iterator<Item = Span> + '_ {
638 iter::Iter::new(self)
639 }
640
641 pub fn get_spans(&self) -> Vec<Span> {
642 self.iter().collect()
643 }
644
645 pub fn iter_range(&self, _range: impl RangeBounds<usize>) {
646 todo!()
647 }
648
649 pub fn len(&self) -> usize {
650 self.content.root_cache().len as usize
651 }
652
653 pub fn len_utf16(&self) -> usize {
654 self.content.root_cache().utf16_len as usize
655 }
656
657 fn len_with(&self, index_type: IndexType) -> usize {
658 match index_type {
659 IndexType::Utf8 => self.content.root_cache().len as usize,
660 IndexType::Utf16 => self.content.root_cache().utf16_len as usize,
661 }
662 }
663
664 pub fn is_empty(&self) -> bool {
665 self.len() == 0
666 }
667
668 pub fn utf16_len(&self) -> usize {
669 self.content.root_cache().utf16_len as usize
670 }
671
672 pub fn export(&self, vv: &VersionVector) -> Vec<u8> {
673 encode(self.store.export(vv))
674 }
675
676 pub fn import(&mut self, data: &[u8]) {
677 self.import_inner(decode(data));
678 }
679
680 fn apply(&mut self, op: Op) {
681 debug_log::group!("apply op");
682 'apply: {
683 match &op.content {
684 OpContent::Ann(ann) => {
685 let ann_idx = self.ann.register(ann.clone());
686 match ann.range.start.id {
687 Some(start_id) => {
688 let cursor = self.find_cursor(start_id);
689 self.content.update_leaf(cursor.leaf, |elements| {
690 let index = cursor.elem_index;
691 let offset = cursor.offset;
692 let type_ = ann.range.start.type_;
693 let is_start = true;
694 insert_anchor_to_char(
695 elements, index, offset, ann_idx, type_, is_start,
696 );
697 (
698 true,
699 Some(AnchorSetDiff::from_ann(ann_idx, is_start).into()),
700 )
701 });
702 }
703 None => {
704 self.init_styles.insert_start(ann_idx);
705 }
706 }
707
708 if let Some(end_id) = ann.range.end.id {
709 let cursor = self.find_cursor(end_id);
710 self.content.update_leaf(cursor.leaf, |elements| {
711 let index = cursor.elem_index;
712 let offset = cursor.offset;
713 let type_ = ann.range.end.type_;
714 let is_start = false;
715 insert_anchor_to_char(
716 elements, index, offset, ann_idx, type_, is_start,
717 );
718 (
719 true,
720 Some(AnchorSetDiff::from_ann(ann_idx, is_start).into()),
721 )
722 });
723 }
724 }
725 OpContent::Text(text) => {
726 let right = match self.find_right(text, &op) {
727 Some(value) => value,
728 None => break 'apply,
729 };
730
731 if let Some(right) = right {
732 self.content.insert_by_query_result(
733 right,
734 Elem::new(op.id, text.left, text.right, text.text.clone()),
735 );
736 } else {
737 self.content.push(Elem::new(
738 op.id,
739 text.left,
740 text.right,
741 text.text.clone(),
742 ));
743 }
744 }
745 OpContent::Del(del) => {
746 let del = del.positive();
747 self.update_elem_in_id_range(del.start, del.len as usize, |elem| {
748 elem.apply_remote_delete()
749 })
750 }
751 }
752 }
753
754 debug_log::group_end!();
755 }
756
757 fn find_right(&mut self, elt: &op::TextInsertOp, op: &Op) -> Option<Option<QueryResult>> {
758 let scan_start = self.find_next_cursor_of(elt.left);
761 if scan_start.is_none() {
762 self.content
764 .push(Elem::new(op.id, elt.left, elt.right, elt.text.clone()));
765 return None;
766 }
767 let scan_start = scan_start.unwrap();
768 let iterator = self.content.iter_range(scan_start..);
769 let elt_left_origin = elt.left;
770 let elt_right_origin = elt.right;
771 let mut elt_right_parent: Option<Option<QueryResult>> = None; let mut visited_id_spans: SmallVec<[IdSpan; 8]> = SmallVec::new();
773 let mut left = None;
774 let mut scanning = false;
775 for o_slice in iterator {
776 let offset = o_slice.start.unwrap_or(0);
778 let o_left_origin = if offset == 0 {
779 o_slice.elem.left
780 } else {
781 Some(o_slice.elem.id.inc(offset as u32 - 1))
782 };
783
784 let end_offset = if let Some(right) = elt.right {
785 if o_slice.elem.contains_id(right) {
786 (right.counter - o_slice.elem.id.counter) as usize
787 } else {
788 o_slice.elem.rle_len()
789 }
790 } else {
791 o_slice.elem.rle_len()
792 };
793
794 if end_offset == offset {
795 break;
796 }
797 if o_left_origin != elt.left
799 && (o_left_origin.is_none()
800 || visited_id_spans
801 .iter()
802 .all(|x| !x.contains(o_left_origin.unwrap())))
803 {
804 break;
805 }
806
807 visited_id_spans.push(IdSpan::new(
808 o_slice.elem.id.inc(offset as u32),
809 end_offset - offset,
810 ));
811
812 if o_left_origin == elt.left {
813 let o_right_origin = o_slice.elem.right;
814 if o_right_origin == elt_right_origin {
815 if o_slice.elem.id.client > op.id.client {
816 break;
817 } else {
818 scanning = false;
819 }
820 } else {
821 let o_right_cursor = o_slice.elem.right.map(|x| self.find_cursor(x));
825 let o_right_parent = o_right_cursor.and_then(|x| {
826 if self.find_left_origin(x) == elt_left_origin {
827 Some(x)
828 } else {
829 None
830 }
831 });
832
833 if elt_right_parent.is_none() {
834 let elt_right_cursor = elt.right.map(|x| self.find_cursor(x));
835 elt_right_parent = Some(elt_right_cursor.and_then(|x| {
836 if self.find_left_origin(x) == elt_left_origin {
837 Some(x)
838 } else {
839 None
840 }
841 }));
842 }
843
844 match self.cmp_right_parent_pos(o_right_parent, elt_right_parent.unwrap()) {
845 Ordering::Less => {
846 scanning = true;
847 }
848 Ordering::Equal if o_slice.elem.id.client > op.id.client => {
849 break;
850 }
851 _ => {
852 scanning = false;
853 }
854 }
855 }
856 }
857
858 if !scanning {
859 let mut path = *o_slice.path();
861 path.offset = end_offset - 1;
862 left = Some(path);
863 }
864 }
865
866 match left {
868 Some(left) => Some(self.content.shift_path_by_one_offset(left)),
869 None => Some(Some(scan_start)),
870 }
871 }
872
873 #[inline]
874 fn cmp_right_parent_pos(&self, a: Option<QueryResult>, b: Option<QueryResult>) -> Ordering {
875 match (a, b) {
876 (None, None) => Ordering::Equal,
877 (None, Some(_)) => Ordering::Greater,
878 (Some(_), None) => Ordering::Less,
879 (Some(a), Some(b)) => self.content.compare_pos(a, b),
880 }
881 }
882
883 pub fn merge(&mut self, other: &Self) {
885 let vv = self.store.vv();
886 let exported = other.export(&vv);
887 let exported = decode(&exported);
888 if cfg!(debug_assertions) || cfg!(feature = "test") {
889 let expected = other.store.export(&vv);
890 assert_eq!(exported, expected);
891 }
892
893 self.import_inner(exported);
894 }
895
896 fn import_inner(&mut self, exported: FxHashMap<ClientID, Vec<Op>>) {
897 let mut all_ops = Vec::new();
898 for (_, ops) in exported {
899 for mut op in ops {
900 let op = match self.store.can_apply(&op) {
901 op::CanApply::Yes => op,
902 op::CanApply::Trim(len) => {
903 op.slice_(len as usize..);
904 op
905 }
906 op::CanApply::Pending => {
907 self.pending_ops.push(op);
908 continue;
909 }
910 op::CanApply::Seen => {
911 continue;
912 }
913 };
914 self.store.insert(op.clone());
915 all_ops.push(op);
916 }
917 }
918 all_ops.sort_by(|a, b| a.lamport.cmp(&b.lamport));
919
920 let mut deletions = Vec::new();
924 for op in all_ops.iter() {
925 if let OpContent::Del(_) = &op.content {
926 deletions.push(op.clone());
927 } else {
928 self.apply(op.clone());
929 }
930 }
931
932 for op in deletions {
933 self.apply(op);
934 }
935 }
936
937 pub fn version(&self) -> VersionVector {
938 self.store.vv()
939 }
940
941 fn update_elem_in_id_range(
942 &mut self,
943 mut id: OpID,
944 mut len: usize,
945 mut f: impl FnMut(&mut Elem),
946 ) {
947 while len > 0 {
953 let (insert_leaf, mut leaf_del_len) = self.cursor_map.get_insert(id).unwrap();
954 leaf_del_len = leaf_del_len.min(len);
955 let leaf_del_len = leaf_del_len;
956 let mut left_len = leaf_del_len;
957 self.content.update_leaf(insert_leaf, |elements| {
959 let mut index = 0;
962 loop {
963 let elem = &elements[index];
964 if !elem.overlap(id, leaf_del_len) {
965 index += 1;
966 continue;
967 }
968
969 let offset = if id.counter > elem.id.counter {
970 (id.counter - elem.id.counter) as usize
971 } else {
972 0
973 };
974 let end = elem
975 .rle_len()
976 .min((id.counter + leaf_del_len as Counter - elem.id.counter) as usize);
977 let (new, _) = elements[index].update(offset, end, &mut f);
978 left_len -= end - offset;
979 if !new.is_empty() {
980 let new_len = new.len();
981 elements.splice(index + 1..index + 1, new);
982 index += new_len;
983 }
984 index += 1;
985 if left_len == 0 {
986 break;
987 }
988 }
989 assert_eq!(left_len, 0);
990 (true, None)
992 });
993 id.counter += leaf_del_len as Counter;
994 len -= leaf_del_len;
995 }
996 }
997
998 fn find_cursor(&self, id: OpID) -> QueryResult {
999 let (insert_leaf, _) = self
1001 .cursor_map
1002 .get_insert(id)
1003 .expect("Cannot find target id");
1004 let node = self.content.get_node(insert_leaf);
1005 let mut elem_index = 0;
1006 let elements = &node.elements();
1007 while !elements[elem_index].contains_id(id) {
1008 elem_index += 1;
1010 }
1011
1012 let offset = (id.counter - elements[elem_index].id.counter) as usize;
1013 assert!(offset < elements[elem_index].atom_len());
1014 QueryResult {
1015 leaf: insert_leaf,
1016 elem_index,
1017 offset,
1018 found: true,
1019 }
1020 }
1021
1022 fn find_left_origin(&self, cursor: QueryResult) -> Option<OpID> {
1023 let offset = cursor.offset;
1024 let elem_index = cursor.elem_index;
1025 let node = self.content.get_node(cursor.leaf);
1026 let elements = node.elements();
1027 if offset == 0 {
1028 elements[elem_index].left
1029 } else {
1030 Some(elements[elem_index].id.inc(offset as u32 - 1))
1031 }
1032 }
1033
1034 fn find_next_cursor_of(&self, id: Option<OpID>) -> Option<QueryResult> {
1035 match id {
1036 Some(id) => {
1037 let cursor = self.find_cursor(id);
1038 self.content.shift_path_by_one_offset(cursor)
1039 }
1040 None => Some(QueryResult {
1041 leaf: self.content.first_leaf(),
1042 elem_index: 0,
1043 offset: 0,
1044 found: true,
1045 }),
1046 }
1047 }
1048
1049 #[inline(always)]
1050 fn next_lamport(&self) -> u32 {
1051 self.store.next_lamport()
1052 }
1053
1054 #[inline]
1055 #[allow(unused)]
1056 pub(crate) fn check(&self) {
1057 self.content.check();
1058 }
1059
1060 pub fn debug_log(&self, include_content: bool) {
1061 debug_log::debug_log!("Text len = {} (utf16={})", self.len(), self.utf16_len());
1062 debug_log::debug_log!("Nodes len = {}", self.content.node_len());
1063 debug_log::debug_log!("Op len = {}", self.store.op_len());
1064 if include_content {
1065 let mut content_inner = format!("{:#?}", &self.content);
1066 const MAX: usize = 100000;
1067 if content_inner.len() > MAX {
1068 for new_len in MAX.. {
1069 if content_inner.is_char_boundary(new_len) {
1070 content_inner.truncate(new_len);
1071 break;
1072 }
1073 }
1074 }
1075 debug_log::debug_log!("ContentTree = {}", content_inner);
1076 debug_log::debug_log!("Store = {:#?}", &self.store);
1078 }
1079 }
1080
1081 pub fn check_no_mergeable_neighbor(&self) {
1082 let mut leaf_idx = Some(self.content.first_leaf());
1083 while let Some(leaf) = leaf_idx {
1084 let node = self.content.get_node(leaf);
1085 let elements = node.elements();
1086 for i in 0..elements.len() - 1 {
1087 if elements[i].can_merge(&elements[i + 1]) {
1088 self.debug_log(false);
1089 panic!(
1090 "Found mergeable neighbor: \n{:#?} \n{:#?}",
1091 elements[i],
1092 elements[i + 1]
1093 );
1094 }
1095 }
1096
1097 leaf_idx = self.content.next_same_level_node(leaf);
1098 }
1099 }
1100}
1101
1102impl Display for RichText {
1103 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1104 for span in self.content.iter() {
1105 if span.is_dead() {
1106 continue;
1107 }
1108
1109 f.write_str(std::str::from_utf8(&span.string).unwrap())?;
1110 }
1111
1112 Ok(())
1113 }
1114}