Store hints in the new map only

This commit is contained in:
Kirill Bulatov 2023-06-06 23:52:10 +03:00
parent 83f4320b60
commit 78b3c9b88a
2 changed files with 13 additions and 31 deletions

View file

@ -72,9 +72,7 @@ pub use multi_buffer::{
use multi_buffer::{MultiBufferChunks, ToOffsetUtf16}; use multi_buffer::{MultiBufferChunks, ToOffsetUtf16};
use ordered_float::OrderedFloat; use ordered_float::OrderedFloat;
use parking_lot::RwLock; use parking_lot::RwLock;
use project::{ use project::{FormatTrigger, Location, LocationLink, Project, ProjectPath, ProjectTransaction};
FormatTrigger, InlayHint, Location, LocationLink, Project, ProjectPath, ProjectTransaction,
};
use scroll::{ use scroll::{
autoscroll::Autoscroll, OngoingScroll, ScrollAnchor, ScrollManager, ScrollbarAutoHide, autoscroll::Autoscroll, OngoingScroll, ScrollAnchor, ScrollManager, ScrollbarAutoHide,
}; };
@ -539,7 +537,7 @@ pub struct Editor {
gutter_hovered: bool, gutter_hovered: bool,
link_go_to_definition_state: LinkGoToDefinitionState, link_go_to_definition_state: LinkGoToDefinitionState,
copilot_state: CopilotState, copilot_state: CopilotState,
inlay_hints: Arc<InlayHintState>, inlay_hints_version: InlayHintVersion,
_subscriptions: Vec<Subscription>, _subscriptions: Vec<Subscription>,
} }
@ -1156,29 +1154,19 @@ impl CopilotState {
} }
} }
#[derive(Debug, Default)] #[derive(Debug, Default, Clone)]
struct InlayHintState(RwLock<(HashMap<usize, Global>, Vec<InlayHint>)>); struct InlayHintVersion(Arc<RwLock<HashMap<usize, Global>>>);
impl InlayHintState {
fn read(&self) -> Vec<InlayHint> {
self.0.read().1.clone()
}
impl InlayHintVersion {
fn is_newer(&self, timestamp: &HashMap<usize, Global>) -> bool { fn is_newer(&self, timestamp: &HashMap<usize, Global>) -> bool {
let current_timestamp = self.0.read().0.clone(); let current_timestamp = self.0.read();
Self::first_timestamp_newer(timestamp, &current_timestamp) Self::first_timestamp_newer(timestamp, &current_timestamp)
} }
fn update_if_newer( fn update_if_newer(&self, new_timestamp: HashMap<usize, Global>) -> bool {
&self,
new_hints: Vec<InlayHint>,
new_timestamp: HashMap<usize, Global>,
) -> bool {
let mut guard = self.0.write(); let mut guard = self.0.write();
if Self::first_timestamp_newer(&new_timestamp, &guard.0) { if Self::first_timestamp_newer(&new_timestamp, &guard) {
guard.0 = new_timestamp; *guard = new_timestamp;
guard.1 = new_hints;
true true
} else { } else {
false false
@ -1414,7 +1402,7 @@ impl Editor {
hover_state: Default::default(), hover_state: Default::default(),
link_go_to_definition_state: Default::default(), link_go_to_definition_state: Default::default(),
copilot_state: Default::default(), copilot_state: Default::default(),
inlay_hints: Arc::new(InlayHintState::default()), inlay_hints_version: InlayHintVersion::default(),
gutter_hovered: false, gutter_hovered: false,
_subscriptions: vec![ _subscriptions: vec![
cx.observe(&buffer, Self::on_buffer_changed), cx.observe(&buffer, Self::on_buffer_changed),
@ -2694,8 +2682,8 @@ impl Editor {
}, },
); );
let inlay_hints_storage = Arc::clone(&self.inlay_hints); let current_hints_version = self.inlay_hints_version.clone();
if inlay_hints_storage.is_newer(&new_timestamp) { if current_hints_version.is_newer(&new_timestamp) {
cx.spawn(|editor, mut cx| async move { cx.spawn(|editor, mut cx| async move {
let mut new_hints = Vec::new(); let mut new_hints = Vec::new();
for task_result in futures::future::join_all(hint_fetch_tasks).await { for task_result in futures::future::join_all(hint_fetch_tasks).await {
@ -2705,8 +2693,7 @@ impl Editor {
} }
} }
// TODO kb another odd clone, can be avoid all this? hide hints behind a handle? if current_hints_version.update_if_newer(new_timestamp) {
if inlay_hints_storage.update_if_newer(new_hints.clone(), new_timestamp) {
editor editor
.update(&mut cx, |editor, cx| { .update(&mut cx, |editor, cx| {
editor.display_map.update(cx, |display_map, cx| { editor.display_map.update(cx, |display_map, cx| {

View file

@ -879,7 +879,6 @@ impl EditorElement {
for (ix, line_with_invisibles) in layout.position_map.line_layouts.iter().enumerate() { for (ix, line_with_invisibles) in layout.position_map.line_layouts.iter().enumerate() {
let row = start_row + ix as u32; let row = start_row + ix as u32;
line_with_invisibles.draw( line_with_invisibles.draw(
editor,
layout, layout,
row, row,
scroll_top, scroll_top,
@ -1795,7 +1794,6 @@ impl LineWithInvisibles {
fn draw( fn draw(
&self, &self,
editor: &mut Editor,
layout: &LayoutState, layout: &LayoutState,
row: u32, row: u32,
scroll_top: f32, scroll_top: f32,
@ -1819,9 +1817,6 @@ impl LineWithInvisibles {
cx, cx,
); );
// TODO kb bad: syscalls + cloning happen very frequently, check the timestamp first
let new_hints = editor.inlay_hints.read();
self.draw_invisibles( self.draw_invisibles(
&selection_ranges, &selection_ranges,
layout, layout,