From 1354d49563e8f849427a8596ac7299bb2753ec54 Mon Sep 17 00:00:00 2001 From: Jacob Mischka Date: Thu, 15 Jul 2021 17:29:24 -0500 Subject: [PATCH] Listen to VimResized event and resize the window when needed Fixes #156 --- src/shell.rs | 22 +++++++++++++++++++++- src/ui.rs | 35 ++++++++++++++++++++++++++++++++++- 2 files changed, 55 insertions(+), 2 deletions(-) diff --git a/src/shell.rs b/src/shell.rs index e69dae59..f0924a70 100644 --- a/src/shell.rs +++ b/src/shell.rs @@ -524,6 +524,24 @@ impl State { } } + pub fn should_resize(&self, columns: usize, rows: usize) -> bool { + let (w, h) = self.calc_nvim_size(); + columns != h.get() as usize || rows != w.get() as usize + } + + pub fn calc_window_size(&self, columns: usize, rows: usize) -> (usize, usize) { + let &CellMetrics { + line_height, + char_width, + .. + } = self.render_state.borrow().font_ctx.cell_metrics(); + + ( + (columns as f64 * char_width).ceil() as usize, + (rows as f64 * line_height).ceil() as usize, + ) + } + fn calc_nvim_size(&self) -> (NonZeroI64, NonZeroI64) { let &CellMetrics { line_height, @@ -1783,7 +1801,9 @@ impl State { } pub fn option_set(&mut self, name: String, val: Value) -> RepaintMode { - if let "guifont" = name.as_str() { self.set_font_from_value(val) }; + if let "guifont" = name.as_str() { + self.set_font_from_value(val) + }; RepaintMode::Nothing } diff --git a/src/ui.rs b/src/ui.rs index 5d800e1b..32c0dbf2 100644 --- a/src/ui.rs +++ b/src/ui.rs @@ -254,6 +254,14 @@ impl Ui { move |args| set_completeopts(&*shell_ref, args), ); + let comps_ref = self.comps.clone(); + let shell_ref = self.shell.clone(); + let update_size = shell.state.borrow().subscribe( + SubscriptionKey::from("VimResized"), + &["&lines", "&columns"], + move |args| update_window_size(&*comps_ref, &*shell_ref, args), + ); + let comps_ref = self.comps.clone(); let shell_ref = self.shell.clone(); window.connect_delete_event(move |_, _| gtk_delete(&*comps_ref, &*shell_ref)); @@ -289,6 +297,7 @@ impl Ui { &update_title, &update_subtitle, &update_completeopt, + &update_size, &post_config_cmds, mode, ); @@ -312,6 +321,7 @@ impl Ui { update_title: &SubscriptionHandle, update_subtitle: &Option, update_completeopt: &SubscriptionHandle, + update_size: &SubscriptionHandle, post_config_cmds: &Option>, mode: StartMode, ) { @@ -322,6 +332,7 @@ impl Ui { shell.set_autocmds(); shell.run_now(&update_title); shell.run_now(&update_completeopt); + shell.run_now(&update_size); if let Some(ref update_subtitle) = update_subtitle { shell.run_now(&update_subtitle); } @@ -555,7 +566,9 @@ fn on_help_about(window: >k::ApplicationWindow) { let about = AboutDialog::new(); about.set_transient_for(Some(window)); about.set_program_name("NeovimGtk"); - about.set_version(Some(crate::GIT_BUILD_VERSION.unwrap_or(env!("CARGO_PKG_VERSION")))); + about.set_version(Some( + crate::GIT_BUILD_VERSION.unwrap_or(env!("CARGO_PKG_VERSION")), + )); about.set_logo_icon_name(Some("org.daa.NeovimGtk")); about.set_authors(&[env!("CARGO_PKG_AUTHORS")]); about.set_comments(Some(misc::about_comments().as_str())); @@ -629,6 +642,26 @@ fn update_window_title(comps: &Arc>, args: Vec) { window.set_title(filename); } +fn update_window_size(comps: &UiMutex, shell: &RefCell, args: Vec) { + let lines = &args[0]; + let cols = &args[1]; + + if let (Ok(lines), Ok(cols)) = (lines.parse::(), cols.parse::()) { + let state_ref = shell.borrow().state.clone(); + let state = state_ref.borrow(); + + if state.should_resize(cols, lines) { + let (width, height) = state.calc_window_size(cols, lines); + + let comps_ref = comps.clone(); + let comps = comps_ref.borrow(); + let window = comps.window.as_ref().unwrap(); + + window.resize(width as i32, height as i32); + } + } +} + #[derive(Serialize, Deserialize)] struct WindowState { current_width: i32,