diff --git a/Makefile b/Makefile index 4c495e8..fbbee73 100644 --- a/Makefile +++ b/Makefile @@ -6,7 +6,7 @@ build/windows-x86_64: mkdir -p build mkdir -p $@ cargo build -r --target x86_64-pc-windows-gnu - cp target/x86_64-pc-windows-gnu/release/bRAC $@/bin + cp target/x86_64-pc-windows-gnu/release/bRAC.exe $@/bin curl -s https://api.github.com/repos/wingtk/gvsbuild/releases/latest \ | grep -o ".*browser_download_url.*GTK4_Gvsbuild.*_x64.zip.*" \ | cut -d : -f 2,3 \ @@ -21,7 +21,7 @@ build/linux-x86_64: mkdir -p build mkdir -p $@ cargo build -r --target x86_64-unknown-linux-gnu - cp target/x86_64-pc-windows-gnu/release/bRAC $@ + cp target/x86_64-unknown-linux-gnu/release/bRAC $@ clean: rm -r build \ No newline at end of file diff --git a/src/chat/ctx.rs b/src/chat/ctx.rs index 0d4245c..6f481fd 100644 --- a/src/chat/ctx.rs +++ b/src/chat/ctx.rs @@ -7,7 +7,7 @@ use super::config::Config; pub struct Context { pub registered: RwLock>, pub config: RwLock, - pub sender: RwLock>>>, + pub sender: RwLock>>>, pub messages: RwLock>, pub packet_size: AtomicUsize, pub name: RwLock diff --git a/src/chat/gui.rs b/src/chat/gui.rs index f4ba4f4..01e4541 100644 --- a/src/chat/gui.rs +++ b/src/chat/gui.rs @@ -5,7 +5,7 @@ use std::thread; use chrono::Local; -use gtk4 as gtk; +use gtk4::{self as gtk, glib::timeout_add_once}; use gtk::prelude::*; use gtk::gdk::{Cursor, Display, Texture}; @@ -14,8 +14,6 @@ use gtk::gio::{self, ActionEntry, ApplicationFlags, MemoryInputStream, Menu}; use gtk::glib::clone; use gtk::glib::{ self, clone::Downgrade, - idle_add_local, - idle_add_local_once, timeout_add_local, source::timeout_add_local_once, ControlFlow @@ -39,8 +37,12 @@ thread_local!( static GLOBAL: RefCell)>> = RefCell::new(None); ); +pub fn clear_chat_messages(ctx: Arc, message: String) { + let _ = ctx.sender.read().unwrap().clone().unwrap().send((message, true)); +} + pub fn add_chat_message(ctx: Arc, message: String) { - let _ = ctx.sender.read().unwrap().clone().unwrap().send(message); + let _ = ctx.sender.read().unwrap().clone().unwrap().send((message, false)); } fn load_pixbuf(data: &[u8]) -> Pixbuf { @@ -427,7 +429,7 @@ fn build_ui(ctx: Arc, app: &Application) -> UiModel { timeout_add_local(Duration::from_millis(30), { let logo = logo.clone(); let logo_anim = logo_anim.clone(); - + move || { logo.set_pixbuf(Some(&logo_anim.pixbuf())); logo_anim.advance(SystemTime::now()); @@ -504,7 +506,7 @@ fn build_ui(ctx: Arc, app: &Application) -> UiModel { #[weak] ctx, move |_| { if text_entry.text().is_empty() { return; } - idle_add_local_once(clone!( + timeout_add_local_once(Duration::ZERO, clone!( #[weak] text_entry, move || { text_entry.set_text(""); @@ -523,7 +525,7 @@ fn build_ui(ctx: Arc, app: &Application) -> UiModel { #[weak] ctx, move |_| { if text_entry.text().is_empty() { return; } - idle_add_local_once(clone!( + timeout_add_local_once(Duration::ZERO, clone!( #[weak] text_entry, move || { text_entry.set_text(""); @@ -543,14 +545,13 @@ fn build_ui(ctx: Arc, app: &Application) -> UiModel { let scrolled_window_weak = Downgrade::downgrade(&chat_scrolled); - idle_add_local({ + timeout_add_local_once(Duration::ZERO, { let scrolled_window_weak = scrolled_window_weak.clone(); move || { if let Some(o) = scrolled_window_weak.upgrade() { o.vadjustment().set_value(o.vadjustment().upper() - o.vadjustment().page_size()); } - ControlFlow::Break } }); @@ -570,11 +571,10 @@ fn build_ui(ctx: Arc, app: &Application) -> UiModel { move |_| { let scrolled_window_weak = scrolled_window_weak.clone(); - idle_add_local(move || { + timeout_add_local_once(Duration::ZERO, move || { if let Some(o) = scrolled_window_weak.upgrade() { o.vadjustment().set_value(o.vadjustment().upper() - o.vadjustment().page_size()); } - ControlFlow::Break }); } }); @@ -603,12 +603,17 @@ fn setup(ctx: Arc, ui: UiModel) { thread::spawn({ let ctx = ctx.clone(); move || { - while let Ok(message) = receiver.recv() { + while let Ok((message, clear)) = receiver.recv() { let _ = tx.send(message.clone()); let ctx = ctx.clone(); - glib::source::timeout_add_once(Duration::ZERO, move || { + timeout_add_once(Duration::ZERO, move || { GLOBAL.with(|global| { if let Some((ui, rx)) = &*global.borrow() { + if clear { + while let Some(row) = ui.chat_box.last_child() { + ui.chat_box.remove(&row); + } + } let message: String = rx.recv().unwrap(); on_add_message(ctx.clone(), &ui, message); } diff --git a/src/chat/mod.rs b/src/chat/mod.rs index 19869bb..fff8f66 100644 --- a/src/chat/mod.rs +++ b/src/chat/mod.rs @@ -9,7 +9,7 @@ use super::{ util::sanitize_text }; -use gui::add_chat_message; +use gui::{add_chat_message, clear_chat_messages}; use lazy_static::lazy_static; use regex::Regex; @@ -166,6 +166,8 @@ pub fn print_message(ctx: Arc, message: String) -> Result<(), Box) -> Result<(), Box> { + let last_size = ctx.packet_size(); + match read_messages( connect_rac!(ctx), ctx.config(|o| o.max_messages), @@ -176,13 +178,29 @@ pub fn recv_tick(ctx: Arc) -> Result<(), Box> { Ok(Some((messages, size))) => { if ctx.config(|o| o.chunked_enabled) { ctx.add_messages_packet(ctx.config(|o| o.max_messages), messages.clone(), size); - for msg in messages { - add_chat_message(ctx.clone(), msg.clone()); + if last_size == 0 { + if messages.len() >= 1 { + clear_chat_messages(ctx.clone(), messages[0].clone()); + if messages.len() >= 2 { + for msg in &messages[1..] { + add_chat_message(ctx.clone(), msg.clone()); + } + } + } + } else { + for msg in messages { + add_chat_message(ctx.clone(), msg.clone()); + } } } else { ctx.put_messages_packet(ctx.config(|o| o.max_messages), messages.clone(), size); - for msg in messages { - add_chat_message(ctx.clone(), msg.clone()); + if messages.len() >= 1 { + clear_chat_messages(ctx.clone(), messages[0].clone()); + if messages.len() >= 2 { + for msg in &messages[1..] { + add_chat_message(ctx.clone(), msg.clone()); + } + } } } },