From fc01d4eecc6bb5c1162d001178d966c0a563c10f Mon Sep 17 00:00:00 2001 From: Em Zhan Date: Sun, 27 Apr 2025 17:11:24 -0500 Subject: [PATCH 1/4] Stack picker and preview vertically if too narrow Co-authored-by: Jesse Luehrs --- helix-term/src/ui/picker.rs | 47 +++++++++++++++++++++++++++++-------- 1 file changed, 37 insertions(+), 10 deletions(-) diff --git a/helix-term/src/ui/picker.rs b/helix-term/src/ui/picker.rs index a6ce91a67..d6c07593a 100644 --- a/helix-term/src/ui/picker.rs +++ b/helix-term/src/ui/picker.rs @@ -57,6 +57,7 @@ use self::handlers::{DynamicQueryChange, DynamicQueryHandler, PreviewHighlightHa pub const ID: &str = "picker"; pub const MIN_AREA_WIDTH_FOR_PREVIEW: u16 = 72; +pub const MIN_AREA_HEIGHT_FOR_PREVIEW: u16 = 24; /// Biggest file size to preview in bytes pub const MAX_FILE_SIZE_FOR_PREVIEW: u64 = 10 * 1024 * 1024; @@ -988,27 +989,50 @@ impl Picker { impl Component for Picker { fn render(&mut self, area: Rect, surface: &mut Surface, cx: &mut Context) { + // default render // +---------+ +---------+ // |prompt | |preview | // +---------+ | | // |picker | | | // | | | | // +---------+ +---------+ + // + // stack vertically + // +---------+ + // |prompt | + // +---------+ + // |picker | + // | | + // +---------+ + // |preview | + // | | + // | | + // +---------+ - let render_preview = - self.show_preview && self.file_fn.is_some() && area.width > MIN_AREA_WIDTH_FOR_PREVIEW; + let render_preview = self.show_preview + && self.file_fn.is_some() + && area.width >= MIN_AREA_WIDTH_FOR_PREVIEW + && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; + let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; - let picker_width = if render_preview { - area.width / 2 + let picker_area = if render_preview { + if stack_vertically { + area.with_height(area.height / 3) + } else { + area.with_width(area.width / 2) + } } else { - area.width + area }; - let picker_area = area.with_width(picker_width); self.render_picker(picker_area, surface, cx); if render_preview { - let preview_area = area.clip_left(picker_width); + let preview_area = if stack_vertically { + area.clip_top(picker_area.height) + } else { + area.clip_left(picker_area.width) + }; self.render_preview(preview_area, surface, cx); } } @@ -1135,10 +1159,13 @@ impl Component for Picker MIN_AREA_WIDTH_FOR_PREVIEW; + let render_preview = self.show_preview + && self.file_fn.is_some() + && area.width >= MIN_AREA_WIDTH_FOR_PREVIEW + && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; + let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; - let picker_width = if render_preview { + let picker_width = if render_preview && !stack_vertically { area.width / 2 } else { area.width From 009024a72079868cae737a0cacf694c4a55a6899 Mon Sep 17 00:00:00 2001 From: Em Zhan Date: Mon, 9 Jun 2025 23:28:27 -0500 Subject: [PATCH 2/4] Refactor common logic into helper function --- helix-term/src/ui/picker.rs | 29 ++++++++++++++--------------- 1 file changed, 14 insertions(+), 15 deletions(-) diff --git a/helix-term/src/ui/picker.rs b/helix-term/src/ui/picker.rs index d6c07593a..b8b25ff92 100644 --- a/helix-term/src/ui/picker.rs +++ b/helix-term/src/ui/picker.rs @@ -1009,12 +1009,7 @@ impl Component for Picker= MIN_AREA_WIDTH_FOR_PREVIEW - && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; - let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; - + let (render_preview, stack_vertically) = self.get_picker_layout(area); let picker_area = if render_preview { if stack_vertically { area.with_height(area.height / 3) @@ -1158,21 +1153,15 @@ impl Component for Picker= MIN_AREA_WIDTH_FOR_PREVIEW - && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; - let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; - + let (render_preview, stack_vertically) = self.get_picker_layout(area); let picker_width = if render_preview && !stack_vertically { area.width / 2 } else { area.width }; - let area = inner.clip_left(1).with_height(1).with_width(picker_width); + let prompt_area = inner.clip_left(1).with_height(1).with_width(picker_width); - self.prompt.cursor(area, editor) + self.prompt.cursor(prompt_area, editor) } fn required_size(&mut self, (width, height): (u16, u16)) -> Option<(u16, u16)> { @@ -1190,5 +1179,15 @@ impl Drop for Picker { self.version.fetch_add(1, atomic::Ordering::Relaxed); } } +impl Picker { + fn get_picker_layout(&self, area: Rect) -> (bool, bool) { + let render_preview = self.show_preview + && self.file_fn.is_some() + && area.width >= MIN_AREA_WIDTH_FOR_PREVIEW + && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; + let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; + return (render_preview, stack_vertically); + } +} type PickerCallback = Box; From 9c0f960ad44a268b1fae65785d9de7960e90af98 Mon Sep 17 00:00:00 2001 From: Em Zhan Date: Mon, 9 Jun 2025 23:35:08 -0500 Subject: [PATCH 3/4] Fix `cargo clippy` error --- helix-term/src/ui/picker.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/helix-term/src/ui/picker.rs b/helix-term/src/ui/picker.rs index b8b25ff92..24487c426 100644 --- a/helix-term/src/ui/picker.rs +++ b/helix-term/src/ui/picker.rs @@ -1186,7 +1186,7 @@ impl Picker { && area.width >= MIN_AREA_WIDTH_FOR_PREVIEW && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; - return (render_preview, stack_vertically); + (render_preview, stack_vertically) } } From 3b944bb947d5751ebdb15a44abc96342e9dcaa99 Mon Sep 17 00:00:00 2001 From: Em Zhan Date: Tue, 10 Jun 2025 08:44:23 -0500 Subject: [PATCH 4/4] Use existing `impl` for helper function --- helix-term/src/ui/picker.rs | 23 +++++++++++------------ 1 file changed, 11 insertions(+), 12 deletions(-) diff --git a/helix-term/src/ui/picker.rs b/helix-term/src/ui/picker.rs index 24487c426..360b000f6 100644 --- a/helix-term/src/ui/picker.rs +++ b/helix-term/src/ui/picker.rs @@ -985,6 +985,15 @@ impl Picker { ); } } + + fn get_layout(&self, area: Rect) -> (bool, bool) { + let render_preview = self.show_preview + && self.file_fn.is_some() + && area.width >= MIN_AREA_WIDTH_FOR_PREVIEW + && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; + let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; + (render_preview, stack_vertically) + } } impl Component for Picker { @@ -1009,7 +1018,7 @@ impl Component for Picker Component for Picker Drop for Picker { self.version.fetch_add(1, atomic::Ordering::Relaxed); } } -impl Picker { - fn get_picker_layout(&self, area: Rect) -> (bool, bool) { - let render_preview = self.show_preview - && self.file_fn.is_some() - && area.width >= MIN_AREA_WIDTH_FOR_PREVIEW - && area.height >= MIN_AREA_HEIGHT_FOR_PREVIEW; - let stack_vertically = area.width / 2 < MIN_AREA_WIDTH_FOR_PREVIEW; - (render_preview, stack_vertically) - } -} type PickerCallback = Box;