diff --git a/src/logger.rs b/src/logger.rs index 41a3d05..1973cfb 100644 --- a/src/logger.rs +++ b/src/logger.rs @@ -125,7 +125,7 @@ impl MsgStore for Logger { async fn set_seen(&self, _id: &usize, _seen: bool) {} - async fn set_all_seen(&self, _seen: bool) {} + async fn set_older_seen(&self, _id: &usize, _seen: bool) {} } impl Log for Logger { diff --git a/src/store.rs b/src/store.rs index 81b32b6..14882cf 100644 --- a/src/store.rs +++ b/src/store.rs @@ -130,5 +130,5 @@ pub trait MsgStore { async fn older_msg_id(&self, id: &M::Id) -> Option; async fn newer_msg_id(&self, id: &M::Id) -> Option; async fn set_seen(&self, id: &M::Id, seen: bool); - async fn set_all_seen(&self, seen: bool); + async fn set_older_seen(&self, id: &M::Id, seen: bool); } diff --git a/src/ui/chat/tree.rs b/src/ui/chat/tree.rs index ed740a9..7e41382 100644 --- a/src/ui/chat/tree.rs +++ b/src/ui/chat/tree.rs @@ -97,7 +97,7 @@ impl> InnerTreeViewState { pub fn list_action_key_bindings(&self, bindings: &mut KeyBindingsList) { bindings.binding("s", "toggle current message's seen status"); bindings.binding("S", "mark all visible messages as seen"); - bindings.binding("ctrl+S", "mark all messages as seen"); + bindings.binding("ctrl+s", "mark all older messages as seen"); } async fn handle_action_key_event(&mut self, event: KeyEvent, id: Option<&M::Id>) -> bool { @@ -116,9 +116,14 @@ impl> InnerTreeViewState { } return true; } - key!(Ctrl + 'S') => { - // Ctrl + Shift + s, extra hard to hit accidentally - self.store.set_all_seen(true).await; + key!(Ctrl + 's') => { + if let Some(id) = id { + self.store.set_older_seen(id, true).await; + } else { + self.store + .set_older_seen(&M::last_possible_id(), true) + .await; + } return true; } _ => {} diff --git a/src/vault/euph.rs b/src/vault/euph.rs index 19a0a31..dea7a49 100644 --- a/src/vault/euph.rs +++ b/src/vault/euph.rs @@ -268,9 +268,10 @@ impl MsgStore for EuphVault { let _ = self.vault.tx.send(request.into()); } - async fn set_all_seen(&self, seen: bool) { - let request = EuphRequest::SetAllSeen { + async fn set_older_seen(&self, id: &Snowflake, seen: bool) { + let request = EuphRequest::SetOlderSeen { room: self.room.clone(), + id: *id, seen, }; let _ = self.vault.tx.send(request.into()); @@ -372,8 +373,9 @@ pub(super) enum EuphRequest { id: Snowflake, seen: bool, }, - SetAllSeen { + SetOlderSeen { room: String, + id: Snowflake, seen: bool, }, } @@ -426,7 +428,9 @@ impl EuphRequest { Self::get_newer_msg_id(conn, room, id, result) } EuphRequest::SetSeen { room, id, seen } => Self::set_seen(conn, room, id, seen), - EuphRequest::SetAllSeen { room, seen } => Self::set_all_seen(conn, room, seen), + EuphRequest::SetOlderSeen { room, id, seen } => { + Self::set_older_seen(conn, room, id, seen) + } }; if let Err(e) = result { // If an error occurs here, the rest of the UI will likely panic and @@ -1022,14 +1026,23 @@ impl EuphRequest { Ok(()) } - fn set_all_seen(conn: &Connection, room: String, seen: bool) -> rusqlite::Result<()> { + fn set_older_seen( + conn: &Connection, + room: String, + id: Snowflake, + seen: bool, + ) -> rusqlite::Result<()> { + // TODO Speed up this update + // Maybe with an index on (room, id, seen) and a filter to only set seen + // where it isn't already set correctly? conn.execute( " UPDATE euph_msgs SET seen = :seen WHERE room = :room + AND id <= :id ", - named_params! { ":room": room, ":seen": seen }, + named_params! { ":room": room, ":id": id, ":seen": seen }, )?; Ok(()) }