From 0a306808dacbe65672e243d5474128d561fda97a Mon Sep 17 00:00:00 2001 From: Antonio Scandurra Date: Tue, 11 Oct 2022 11:44:31 +0200 Subject: [PATCH] Dismiss project shared notifications when a project was unshared --- crates/call/src/room.rs | 32 +++++++++++++++++-- .../src/project_shared_notification.rs | 15 ++++++++- 2 files changed, 43 insertions(+), 4 deletions(-) diff --git a/crates/call/src/room.rs b/crates/call/src/room.rs index fb9ba09d814cda6cfaa551ce3fe926fb802ad7c4..ebe2d4284be1e4caf60ae3da62a025d2688f12b0 100644 --- a/crates/call/src/room.rs +++ b/crates/call/src/room.rs @@ -18,6 +18,10 @@ pub enum Event { project_id: u64, worktree_root_names: Vec, }, + RemoteProjectUnshared { + project_id: u64, + }, + Left, } pub struct Room { @@ -148,6 +152,7 @@ impl Room { } cx.notify(); + cx.emit(Event::Left); self.status = RoomStatus::Offline; self.remote_participants.clear(); self.pending_participants.clear(); @@ -223,15 +228,21 @@ impl Room { let peer_id = PeerId(participant.peer_id); this.participant_user_ids.insert(participant.user_id); - let existing_projects = this + let old_projects = this .remote_participants .get(&peer_id) .into_iter() .flat_map(|existing| &existing.projects) .map(|project| project.id) .collect::>(); + let new_projects = participant + .projects + .iter() + .map(|project| project.id) + .collect::>(); + for project in &participant.projects { - if !existing_projects.contains(&project.id) { + if !old_projects.contains(&project.id) { cx.emit(Event::RemoteProjectShared { owner: user.clone(), project_id: project.id, @@ -240,6 +251,12 @@ impl Room { } } + for unshared_project_id in old_projects.difference(&new_projects) { + cx.emit(Event::RemoteProjectUnshared { + project_id: *unshared_project_id, + }); + } + this.remote_participants.insert( peer_id, RemoteParticipant { @@ -252,7 +269,16 @@ impl Room { } this.remote_participants.retain(|_, participant| { - this.participant_user_ids.contains(&participant.user.id) + if this.participant_user_ids.contains(&participant.user.id) { + true + } else { + for project in &participant.projects { + cx.emit(Event::RemoteProjectUnshared { + project_id: project.id, + }); + } + false + } }); cx.notify(); diff --git a/crates/collab_ui/src/project_shared_notification.rs b/crates/collab_ui/src/project_shared_notification.rs index 22383feb20fc3da614654a078b34d2f32e11af9f..a17e11b079f42c2bb863b0dee8cc8f734fcc0aca 100644 --- a/crates/collab_ui/src/project_shared_notification.rs +++ b/crates/collab_ui/src/project_shared_notification.rs @@ -1,5 +1,6 @@ use call::{room, ActiveCall}; use client::User; +use collections::HashMap; use gpui::{ actions, elements::*, @@ -18,6 +19,7 @@ pub fn init(cx: &mut MutableAppContext) { cx.add_action(ProjectSharedNotification::dismiss); let active_call = ActiveCall::global(cx); + let mut notification_windows = HashMap::default(); cx.subscribe(&active_call, move |_, event, cx| match event { room::Event::RemoteProjectShared { owner, @@ -29,7 +31,7 @@ pub fn init(cx: &mut MutableAppContext) { let theme = &cx.global::().theme.project_shared_notification; let window_size = vec2f(theme.window_width, theme.window_height); - cx.add_window( + let (window_id, _) = cx.add_window( WindowOptions { bounds: WindowBounds::Fixed(RectF::new( vec2f(screen_size.x() - window_size.x() - PADDING, PADDING), @@ -48,6 +50,17 @@ pub fn init(cx: &mut MutableAppContext) { ) }, ); + notification_windows.insert(*project_id, window_id); + } + room::Event::RemoteProjectUnshared { project_id } => { + if let Some(window_id) = notification_windows.remove(&project_id) { + cx.remove_window(window_id); + } + } + room::Event::Left => { + for (_, window_id) in notification_windows.drain() { + cx.remove_window(window_id); + } } }) .detach();