From d5ed69ebf944c5a0d4d30ed3ec53fb12f820add9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20DOUIN?= Date: Mon, 3 May 2021 22:10:03 +0200 Subject: [PATCH] fix overflow panic when shrink column (#138) --- CHANGELOG.md | 2 ++ src/table.rs | 49 ++++++++++++++++++++++++++++++++++++------------- 2 files changed, 38 insertions(+), 13 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 083ccf6..421ce5f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Fixed - Table with subject containing `\r` or `\n`[#141] +- Overflow panic when shrink column [#138] ## [0.3.0] - 2021-04-28 @@ -229,4 +230,5 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 [#131]: https://github.com/soywod/himalaya/issues/131 [#132]: https://github.com/soywod/himalaya/issues/132 [#133]: https://github.com/soywod/himalaya/issues/133 +[#138]: https://github.com/soywod/himalaya/issues/138 [#141]: https://github.com/soywod/himalaya/issues/141 diff --git a/src/table.rs b/src/table.rs index 8459dec..7e50d7f 100644 --- a/src/table.rs +++ b/src/table.rs @@ -2,6 +2,9 @@ use log::{debug, trace}; use std::fmt; use unicode_width::UnicodeWidthStr; +const DEFAULT_TERM_WIDTH: usize = 80; +const MAX_SHRINK_WIDTH: usize = 5; + #[derive(Debug)] pub struct Style(u8, u8, u8); @@ -148,7 +151,7 @@ where fn max_width() -> usize { terminal_size::terminal_size() .map(|(w, _)| w.0 as usize) - .unwrap_or(80) + .unwrap_or(DEFAULT_TERM_WIDTH) } fn build(items: &[Self]) -> Vec> { @@ -191,11 +194,15 @@ where let shrink_width = table_width - Self::max_width(); trace!("shrink_width: {}", shrink_width); - let cell_width = cell_widths[i] - shrink_width; - let cell_is_overflowing = cell.unicode_width() > cell_width; + let cell_width = if shrink_width + MAX_SHRINK_WIDTH < cell_widths[i] { + cell_widths[i] - shrink_width + } else { + MAX_SHRINK_WIDTH + }; trace!("cell_width: {}", cell_width); trace!("cell unicode_width: {}", cell.unicode_width()); + let cell_is_overflowing = cell.unicode_width() > cell_width; if cell_is_overflowing { trace!("cell is overflowing"); @@ -346,13 +353,13 @@ mod tests { } #[test] - fn shrink() { + fn basic_shrink() { let items = vec![ - Item::new(1, "short", "desc"), - Item::new(2, "loooooong", "desc"), - Item::new(3, "shriiiiink", "desc"), - Item::new(4, "shriiiiiiiiiink", "desc"), - Item::new(5, "", "desc"), + Item::new(1, "", "desc"), + Item::new(2, "short", "desc"), + Item::new(3, "loooooong", "desc"), + Item::new(4, "shriiiiink", "desc"), + Item::new(5, "shriiiiiiiiiink", "desc"), Item::new(6, "😍😍😍😍", "desc"), Item::new(7, "😍😍😍😍😍", "desc"), Item::new(8, "!😍😍😍😍😍", "desc"), @@ -360,11 +367,11 @@ mod tests { let table = vec![ vec!["ID ", "NAME ", "DESC "], - vec!["1 ", "short ", "desc "], - vec!["2 ", "loooooong ", "desc "], - vec!["3 ", "shriiiii… ", "desc "], + vec!["1 ", " ", "desc "], + vec!["2 ", "short ", "desc "], + vec!["3 ", "loooooong ", "desc "], vec!["4 ", "shriiiii… ", "desc "], - vec!["5 ", " ", "desc "], + vec!["5 ", "shriiiii… ", "desc "], vec!["6 ", "😍😍😍😍 ", "desc "], vec!["7 ", "πŸ˜πŸ˜πŸ˜πŸ˜β€¦ ", "desc "], vec!["8 ", "!πŸ˜πŸ˜πŸ˜β€¦ ", "desc "], @@ -372,4 +379,20 @@ mod tests { assert_eq!(table, Table::build(&items)); } + + #[test] + fn max_shrink_width() { + let items = vec![ + Item::new(1111, "shriiiiiiiink", "desc very looong"), + Item::new(2222, "shriiiiiiiink", "desc very loooooooooong"), + ]; + + let table = vec![ + vec!["ID ", "NAME ", "DESC "], + vec!["1111 ", "shri… ", "desc very looong "], + vec!["2222 ", "shri… ", "desc very loooooooooong "], + ]; + + assert_eq!(table, Table::build(&items)); + } }