diff --git a/crates/ai/src/assistant.rs b/crates/ai/src/assistant.rs index 6d4fce2f6d09de085f2e78e8f10aeaad8c0bd16c..2376a1ff8764665d7a63a86a975f7820c789961e 100644 --- a/crates/ai/src/assistant.rs +++ b/crates/ai/src/assistant.rs @@ -702,7 +702,7 @@ impl AssistantPanel { } if foreground_ranges.is_empty() { - editor.clear_text_highlights::(cx); + editor.clear_highlights::(cx); } else { editor.highlight_text::( foreground_ranges, diff --git a/crates/editor/src/display_map.rs b/crates/editor/src/display_map.rs index d0cb7fd045812b0bca1043a35ab7518000e1905f..3ead02408d79febc1a074747bd5e1412985ccf43 100644 --- a/crates/editor/src/display_map.rs +++ b/crates/editor/src/display_map.rs @@ -43,8 +43,8 @@ pub trait ToDisplayPoint { fn to_display_point(&self, map: &DisplaySnapshot) -> DisplayPoint; } -// TODO kb InlayHighlights = ... ? type TextHighlights = TreeMap, Arc<(HighlightStyle, Vec>)>>; +type InlayHighlights = TreeMap, Arc<(HighlightStyle, Vec)>>; pub struct DisplayMap { buffer: ModelHandle, @@ -55,6 +55,7 @@ pub struct DisplayMap { wrap_map: ModelHandle, block_map: BlockMap, text_highlights: TextHighlights, + inlay_highlights: InlayHighlights, pub clip_at_line_ends: bool, } @@ -90,6 +91,7 @@ impl DisplayMap { wrap_map, block_map, text_highlights: Default::default(), + inlay_highlights: Default::default(), clip_at_line_ends: false, } } @@ -114,6 +116,7 @@ impl DisplayMap { wrap_snapshot, block_snapshot, text_highlights: self.text_highlights.clone(), + inlay_highlights: self.inlay_highlights.clone(), clip_at_line_ends: self.clip_at_line_ends, } } @@ -226,26 +229,18 @@ impl DisplayMap { ranges: Vec, style: HighlightStyle, ) { - // TODO kb - // self.text_highlights.insert( - // Some(type_id), - // Arc::new(( - // style, - // ranges.into_iter().map(DocumentRange::Inlay).collect(), - // )), - // ); + self.inlay_highlights + .insert(Some(type_id), Arc::new((style, ranges))); } pub fn text_highlights(&self, type_id: TypeId) -> Option<(HighlightStyle, &[Range])> { let highlights = self.text_highlights.get(&Some(type_id))?; Some((highlights.0, &highlights.1)) } - - pub fn clear_text_highlights( - &mut self, - type_id: TypeId, - ) -> Option>)>> { - self.text_highlights.remove(&Some(type_id)) + pub fn clear_highlights(&mut self, type_id: TypeId) -> bool { + let mut cleared = self.text_highlights.remove(&Some(type_id)).is_some(); + cleared |= self.inlay_highlights.remove(&Some(type_id)).is_none(); + cleared } pub fn set_font(&self, font_id: FontId, font_size: f32, cx: &mut ModelContext) -> bool { @@ -317,9 +312,18 @@ pub struct DisplaySnapshot { wrap_snapshot: wrap_map::WrapSnapshot, block_snapshot: block_map::BlockSnapshot, text_highlights: TextHighlights, + inlay_highlights: InlayHighlights, clip_at_line_ends: bool, } +#[derive(Debug, Default)] +pub struct Highlights<'a> { + pub text_highlights: Option<&'a TextHighlights>, + pub inlay_highlights: Option<&'a InlayHighlights>, + pub inlay_highlight_style: Option, + pub suggestion_highlight_style: Option, +} + impl DisplaySnapshot { #[cfg(test)] pub fn fold_count(&self) -> usize { @@ -454,9 +458,7 @@ impl DisplaySnapshot { .chunks( display_row..self.max_point().row() + 1, false, - None, - None, - None, + Highlights::default(), ) .map(|h| h.text) } @@ -465,7 +467,7 @@ impl DisplaySnapshot { pub fn reverse_text_chunks(&self, display_row: u32) -> impl Iterator { (0..=display_row).into_iter().rev().flat_map(|row| { self.block_snapshot - .chunks(row..row + 1, false, None, None, None) + .chunks(row..row + 1, false, Highlights::default()) .map(|h| h.text) .collect::>() .into_iter() @@ -477,15 +479,18 @@ impl DisplaySnapshot { &self, display_rows: Range, language_aware: bool, - hint_highlight_style: Option, + inlay_highlight_style: Option, suggestion_highlight_style: Option, ) -> DisplayChunks<'_> { self.block_snapshot.chunks( display_rows, language_aware, - Some(&self.text_highlights), - hint_highlight_style, - suggestion_highlight_style, + Highlights { + text_highlights: Some(&self.text_highlights), + inlay_highlights: Some(&self.inlay_highlights), + inlay_highlight_style, + suggestion_highlight_style, + }, ) } @@ -743,7 +748,7 @@ impl DisplaySnapshot { } #[cfg(any(test, feature = "test-support"))] - pub fn highlight_ranges( + pub fn text_highlight_ranges( &self, ) -> Option>)>> { let type_id = TypeId::of::(); diff --git a/crates/editor/src/display_map/block_map.rs b/crates/editor/src/display_map/block_map.rs index 741507004cc9bc0064ba682701310b832111438f..e54ac04d89c4d1f919730dc20b8844132f4c393d 100644 --- a/crates/editor/src/display_map/block_map.rs +++ b/crates/editor/src/display_map/block_map.rs @@ -1,10 +1,10 @@ use super::{ wrap_map::{self, WrapEdit, WrapPoint, WrapSnapshot}, - TextHighlights, + Highlights, }; use crate::{Anchor, Editor, ExcerptId, ExcerptRange, ToPoint as _}; use collections::{Bound, HashMap, HashSet}; -use gpui::{fonts::HighlightStyle, AnyElement, ViewContext}; +use gpui::{AnyElement, ViewContext}; use language::{BufferSnapshot, Chunk, Patch, Point}; use parking_lot::Mutex; use std::{ @@ -576,9 +576,7 @@ impl BlockSnapshot { self.chunks( 0..self.transforms.summary().output_rows, false, - None, - None, - None, + Highlights::default(), ) .map(|chunk| chunk.text) .collect() @@ -588,9 +586,7 @@ impl BlockSnapshot { &'a self, rows: Range, language_aware: bool, - text_highlights: Option<&'a TextHighlights>, - hint_highlight_style: Option, - suggestion_highlight_style: Option, + highlights: Highlights<'a>, ) -> BlockChunks<'a> { let max_output_row = cmp::min(rows.end, self.transforms.summary().output_rows); let mut cursor = self.transforms.cursor::<(BlockRow, WrapRow)>(); @@ -622,9 +618,7 @@ impl BlockSnapshot { input_chunks: self.wrap_snapshot.chunks( input_start..input_end, language_aware, - text_highlights, - hint_highlight_style, - suggestion_highlight_style, + highlights, ), input_chunk: Default::default(), transforms: cursor, @@ -1501,9 +1495,7 @@ mod tests { .chunks( start_row as u32..blocks_snapshot.max_point().row + 1, false, - None, - None, - None, + Highlights::default(), ) .map(|chunk| chunk.text) .collect::(); diff --git a/crates/editor/src/display_map/fold_map.rs b/crates/editor/src/display_map/fold_map.rs index d5473027a6b0145bad28f21c1e91ce7491f9eb63..8faa0c3ec2cc8cc74a87d7d98e2ee8181127e960 100644 --- a/crates/editor/src/display_map/fold_map.rs +++ b/crates/editor/src/display_map/fold_map.rs @@ -1,6 +1,6 @@ use super::{ inlay_map::{InlayBufferRows, InlayChunks, InlayEdit, InlayOffset, InlayPoint, InlaySnapshot}, - TextHighlights, + Highlights, }; use crate::{Anchor, AnchorRangeExt, MultiBufferSnapshot, ToOffset}; use gpui::{color::Color, fonts::HighlightStyle}; @@ -475,7 +475,7 @@ pub struct FoldSnapshot { impl FoldSnapshot { #[cfg(test)] pub fn text(&self) -> String { - self.chunks(FoldOffset(0)..self.len(), false, None, None, None) + self.chunks(FoldOffset(0)..self.len(), false, Highlights::default()) .map(|c| c.text) .collect() } @@ -651,9 +651,7 @@ impl FoldSnapshot { &'a self, range: Range, language_aware: bool, - text_highlights: Option<&'a TextHighlights>, - hint_highlight_style: Option, - suggestion_highlight_style: Option, + highlights: Highlights<'a>, ) -> FoldChunks<'a> { let mut transform_cursor = self.transforms.cursor::<(FoldOffset, InlayOffset)>(); @@ -674,9 +672,7 @@ impl FoldSnapshot { inlay_chunks: self.inlay_snapshot.chunks( inlay_start..inlay_end, language_aware, - text_highlights, - hint_highlight_style, - suggestion_highlight_style, + highlights, ), inlay_chunk: None, inlay_offset: inlay_start, @@ -687,8 +683,12 @@ impl FoldSnapshot { } pub fn chars_at(&self, start: FoldPoint) -> impl '_ + Iterator { - self.chunks(start.to_offset(self)..self.len(), false, None, None, None) - .flat_map(|chunk| chunk.text.chars()) + self.chunks( + start.to_offset(self)..self.len(), + false, + Highlights::default(), + ) + .flat_map(|chunk| chunk.text.chars()) } #[cfg(test)] @@ -1496,7 +1496,7 @@ mod tests { let text = &expected_text[start.0..end.0]; assert_eq!( snapshot - .chunks(start..end, false, None, None, None) + .chunks(start..end, false, Highlights::default()) .map(|c| c.text) .collect::(), text, diff --git a/crates/editor/src/display_map/inlay_map.rs b/crates/editor/src/display_map/inlay_map.rs index 45cb7ec7f3394d0b80252a118a1ff76a9109da60..51b6806cd1809e1139323b747f3d7f1cd90d68e3 100644 --- a/crates/editor/src/display_map/inlay_map.rs +++ b/crates/editor/src/display_map/inlay_map.rs @@ -15,7 +15,7 @@ use std::{ use sum_tree::{Bias, Cursor, SumTree}; use text::{Patch, Rope}; -use super::TextHighlights; +use super::Highlights; pub struct InlayMap { snapshot: InlaySnapshot, @@ -213,7 +213,7 @@ pub struct InlayChunks<'a> { inlay_chunk: Option<&'a str>, output_offset: InlayOffset, max_output_offset: InlayOffset, - hint_highlight_style: Option, + inlay_highlight_style: Option, suggestion_highlight_style: Option, highlight_endpoints: Peekable>, active_highlights: BTreeMap, HighlightStyle>, @@ -314,7 +314,7 @@ impl<'a> Iterator for InlayChunks<'a> { self.output_offset.0 += chunk.len(); let mut highlight_style = match inlay.id { InlayId::Suggestion(_) => self.suggestion_highlight_style, - InlayId::Hint(_) => self.hint_highlight_style, + InlayId::Hint(_) => self.inlay_highlight_style, }; if !self.active_highlights.is_empty() { for active_highlight in self.active_highlights.values() { @@ -991,15 +991,13 @@ impl InlaySnapshot { &'a self, range: Range, language_aware: bool, - text_highlights: Option<&'a TextHighlights>, - hint_highlight_style: Option, - suggestion_highlight_style: Option, + highlights: Highlights<'a>, ) -> InlayChunks<'a> { let mut cursor = self.transforms.cursor::<(InlayOffset, usize)>(); cursor.seek(&range.start, Bias::Right, &()); let mut highlight_endpoints = Vec::new(); - if let Some(text_highlights) = text_highlights { + if let Some(text_highlights) = highlights.text_highlights { if !text_highlights.is_empty() { while cursor.start().0 < range.end { let transform_start = self.buffer.anchor_after( @@ -1065,8 +1063,8 @@ impl InlaySnapshot { buffer_chunk: None, output_offset: range.start, max_output_offset: range.end, - hint_highlight_style, - suggestion_highlight_style, + inlay_highlight_style: highlights.inlay_highlight_style, + suggestion_highlight_style: highlights.suggestion_highlight_style, highlight_endpoints: highlight_endpoints.into_iter().peekable(), active_highlights: Default::default(), snapshot: self, @@ -1075,7 +1073,7 @@ impl InlaySnapshot { #[cfg(test)] pub fn text(&self) -> String { - self.chunks(Default::default()..self.len(), false, None, None, None) + self.chunks(Default::default()..self.len(), false, Highlights::default()) .map(|chunk| chunk.text) .collect() } @@ -1123,7 +1121,7 @@ fn push_isomorphic(sum_tree: &mut SumTree, summary: TextSummary) { #[cfg(test)] mod tests { use super::*; - use crate::{InlayId, MultiBuffer}; + use crate::{display_map::TextHighlights, InlayId, MultiBuffer}; use gpui::AppContext; use project::{InlayHint, InlayHintLabel, ResolveState}; use rand::prelude::*; @@ -1619,7 +1617,7 @@ mod tests { ); } - let mut highlights = TextHighlights::default(); + let mut text_highlights = TextHighlights::default(); let highlight_count = rng.gen_range(0_usize..10); let mut highlight_ranges = (0..highlight_count) .map(|_| buffer_snapshot.random_byte_range(0, &mut rng)) @@ -1634,7 +1632,7 @@ mod tests { ..buffer_snapshot.anchor_after(range.end) }) .collect::>(); - highlights.insert( + text_highlights.insert( Some(TypeId::of::<()>()), Arc::new((HighlightStyle::default(), highlight_ranges)), ); @@ -1649,9 +1647,12 @@ mod tests { .chunks( InlayOffset(start)..InlayOffset(end), false, - Some(&highlights), - None, - None, + Highlights { + text_highlights: Some(&text_highlights), + inlay_highlights: None, + inlay_highlight_style: None, + suggestion_highlight_style: None, + }, ) .map(|chunk| chunk.text) .collect::(); diff --git a/crates/editor/src/display_map/tab_map.rs b/crates/editor/src/display_map/tab_map.rs index 2cf0471b37889a5cf5d3db26cfe3d1de91dc8e20..6b38ea2d243e77fcb8ea16e8d2d29ba83c4b003b 100644 --- a/crates/editor/src/display_map/tab_map.rs +++ b/crates/editor/src/display_map/tab_map.rs @@ -1,9 +1,8 @@ use super::{ fold_map::{self, FoldChunks, FoldEdit, FoldPoint, FoldSnapshot}, - TextHighlights, + Highlights, }; use crate::MultiBufferSnapshot; -use gpui::fonts::HighlightStyle; use language::{Chunk, Point}; use std::{cmp, mem, num::NonZeroU32, ops::Range}; use sum_tree::Bias; @@ -68,9 +67,7 @@ impl TabMap { 'outer: for chunk in old_snapshot.fold_snapshot.chunks( fold_edit.old.end..old_end_row_successor_offset, false, - None, - None, - None, + Highlights::default(), ) { for (ix, _) in chunk.text.match_indices('\t') { let offset_from_edit = offset_from_edit + (ix as u32); @@ -183,7 +180,7 @@ impl TabSnapshot { self.max_point() }; for c in self - .chunks(range.start..line_end, false, None, None, None) + .chunks(range.start..line_end, false, Highlights::default()) .flat_map(|chunk| chunk.text.chars()) { if c == '\n' { @@ -200,9 +197,7 @@ impl TabSnapshot { .chunks( TabPoint::new(range.end.row(), 0)..range.end, false, - None, - None, - None, + Highlights::default(), ) .flat_map(|chunk| chunk.text.chars()) { @@ -223,9 +218,7 @@ impl TabSnapshot { &'a self, range: Range, language_aware: bool, - text_highlights: Option<&'a TextHighlights>, - hint_highlight_style: Option, - suggestion_highlight_style: Option, + highlights: Highlights<'a>, ) -> TabChunks<'a> { let (input_start, expanded_char_column, to_next_stop) = self.to_fold_point(range.start, Bias::Left); @@ -245,9 +238,7 @@ impl TabSnapshot { fold_chunks: self.fold_snapshot.chunks( input_start..input_end, language_aware, - text_highlights, - hint_highlight_style, - suggestion_highlight_style, + highlights, ), input_column, column: expanded_char_column, @@ -270,9 +261,13 @@ impl TabSnapshot { #[cfg(test)] pub fn text(&self) -> String { - self.chunks(TabPoint::zero()..self.max_point(), false, None, None, None) - .map(|chunk| chunk.text) - .collect() + self.chunks( + TabPoint::zero()..self.max_point(), + false, + Highlights::default(), + ) + .map(|chunk| chunk.text) + .collect() } pub fn max_point(&self) -> TabPoint { @@ -597,9 +592,7 @@ mod tests { .chunks( TabPoint::new(0, ix as u32)..tab_snapshot.max_point(), false, - None, - None, - None, + Highlights::default(), ) .map(|c| c.text) .collect::(), @@ -674,7 +667,8 @@ mod tests { let mut chunks = Vec::new(); let mut was_tab = false; let mut text = String::new(); - for chunk in snapshot.chunks(start..snapshot.max_point(), false, None, None, None) { + for chunk in snapshot.chunks(start..snapshot.max_point(), false, Highlights::default()) + { if chunk.is_tab != was_tab { if !text.is_empty() { chunks.push((mem::take(&mut text), was_tab)); @@ -743,7 +737,7 @@ mod tests { let expected_summary = TextSummary::from(expected_text.as_str()); assert_eq!( tabs_snapshot - .chunks(start..end, false, None, None, None) + .chunks(start..end, false, Highlights::default()) .map(|c| c.text) .collect::(), expected_text, diff --git a/crates/editor/src/display_map/wrap_map.rs b/crates/editor/src/display_map/wrap_map.rs index f3600936f9bf77df6773ad14fd39f4e465398e15..60337661c1abfed638dd861a4c2e9464f70cf2ca 100644 --- a/crates/editor/src/display_map/wrap_map.rs +++ b/crates/editor/src/display_map/wrap_map.rs @@ -1,13 +1,11 @@ use super::{ fold_map::FoldBufferRows, tab_map::{self, TabEdit, TabPoint, TabSnapshot}, - TextHighlights, + Highlights, }; use crate::MultiBufferSnapshot; use gpui::{ - fonts::{FontId, HighlightStyle}, - text_layout::LineWrapper, - AppContext, Entity, ModelContext, ModelHandle, Task, + fonts::FontId, text_layout::LineWrapper, AppContext, Entity, ModelContext, ModelHandle, Task, }; use language::{Chunk, Point}; use lazy_static::lazy_static; @@ -444,9 +442,7 @@ impl WrapSnapshot { let mut chunks = new_tab_snapshot.chunks( TabPoint::new(edit.new_rows.start, 0)..new_tab_snapshot.max_point(), false, - None, - None, - None, + Highlights::default(), ); let mut edit_transforms = Vec::::new(); for _ in edit.new_rows.start..edit.new_rows.end { @@ -575,9 +571,7 @@ impl WrapSnapshot { &'a self, rows: Range, language_aware: bool, - text_highlights: Option<&'a TextHighlights>, - hint_highlight_style: Option, - suggestion_highlight_style: Option, + highlights: Highlights<'a>, ) -> WrapChunks<'a> { let output_start = WrapPoint::new(rows.start, 0); let output_end = WrapPoint::new(rows.end, 0); @@ -594,9 +588,7 @@ impl WrapSnapshot { input_chunks: self.tab_snapshot.chunks( input_start..input_end, language_aware, - text_highlights, - hint_highlight_style, - suggestion_highlight_style, + highlights, ), input_chunk: Default::default(), output_position: output_start, @@ -1323,9 +1315,7 @@ mod tests { self.chunks( wrap_row..self.max_point().row() + 1, false, - None, - None, - None, + Highlights::default(), ) .map(|h| h.text) } @@ -1350,7 +1340,7 @@ mod tests { } let actual_text = self - .chunks(start_row..end_row, true, None, None, None) + .chunks(start_row..end_row, true, Highlights::default()) .map(|c| c.text) .collect::(); assert_eq!( diff --git a/crates/editor/src/editor.rs b/crates/editor/src/editor.rs index 985ca7875e531551e08d7ce68661b220c673c674..5e6eb7f74d0e156be3158e5679f10af1237049cf 100644 --- a/crates/editor/src/editor.rs +++ b/crates/editor/src/editor.rs @@ -7234,7 +7234,7 @@ impl Editor { Some(Autoscroll::fit()), cx, ); - self.clear_text_highlights::(cx); + self.clear_highlights::(cx); self.show_local_selections = true; if moving_cursor { @@ -8038,11 +8038,11 @@ impl Editor { self.display_map.read(cx).text_highlights(TypeId::of::()) } - pub fn clear_text_highlights(&mut self, cx: &mut ViewContext) { - let text_highlights = self + pub fn clear_highlights(&mut self, cx: &mut ViewContext) { + let cleared = self .display_map - .update(cx, |map, _| map.clear_text_highlights(TypeId::of::())); - if text_highlights.is_some() { + .update(cx, |map, _| map.clear_highlights(TypeId::of::())); + if cleared { cx.notify(); } } @@ -8683,7 +8683,7 @@ impl View for Editor { self.link_go_to_definition_state.task = None; - self.clear_text_highlights::(cx); + self.clear_highlights::(cx); } false @@ -8756,7 +8756,7 @@ impl View for Editor { } fn unmark_text(&mut self, cx: &mut ViewContext) { - self.clear_text_highlights::(cx); + self.clear_highlights::(cx); self.ime_transaction.take(); } diff --git a/crates/editor/src/link_go_to_definition.rs b/crates/editor/src/link_go_to_definition.rs index 5663fe146981110c5405752916871a28fe51880a..544a696e0b05fe7b865ee5dcb55ac8bf57407361 100644 --- a/crates/editor/src/link_go_to_definition.rs +++ b/crates/editor/src/link_go_to_definition.rs @@ -444,7 +444,7 @@ pub fn show_link_definition( this.update(&mut cx, |this, cx| { // Clear any existing highlights - this.clear_text_highlights::(cx); + this.clear_highlights::(cx); this.link_go_to_definition_state.kind = Some(definition_kind); this.link_go_to_definition_state.symbol_range = result .as_ref() @@ -545,7 +545,7 @@ pub fn hide_link_definition(editor: &mut Editor, cx: &mut ViewContext) { editor.link_go_to_definition_state.task = None; - editor.clear_text_highlights::(cx); + editor.clear_highlights::(cx); } pub fn go_to_fetched_definition( @@ -1198,7 +1198,7 @@ mod tests { cx.update_editor(|editor, cx| { let snapshot = editor.snapshot(cx); let actual_ranges = snapshot - .highlight_ranges::() + .text_highlight_ranges::() .map(|ranges| ranges.as_ref().clone().1) .unwrap_or_default(); @@ -1233,7 +1233,7 @@ mod tests { cx.update_editor(|editor, cx| { let snapshot = editor.snapshot(cx); let actual_ranges = snapshot - .highlight_ranges::() + .text_highlight_ranges::() .map(|ranges| ranges.as_ref().clone().1) .unwrap_or_default(); diff --git a/crates/editor/src/test/editor_test_context.rs b/crates/editor/src/test/editor_test_context.rs index 118cddaa9226a543ca479f577428237d77539d5d..0bae32f1f7087b05b67f166554671ca6359a6104 100644 --- a/crates/editor/src/test/editor_test_context.rs +++ b/crates/editor/src/test/editor_test_context.rs @@ -236,7 +236,7 @@ impl<'a> EditorTestContext<'a> { let expected_ranges = self.ranges(marked_text); let snapshot = self.update_editor(|editor, cx| editor.snapshot(cx)); let actual_ranges: Vec> = snapshot - .highlight_ranges::() + .text_highlight_ranges::() .map(|ranges| ranges.as_ref().clone().1) .unwrap_or_default() .into_iter()