diff --git a/CHANGELOG.md b/CHANGELOG.md index 6a7f84bf..9485743c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,7 @@ - Add strict clippy lints to improve code consistency and readability. - Expand workflow clippy task to lint all-features in workspace. - Add docs badge to readme. +- Add date select option to apply style to a list of given days [#181](https://github.com/mikaelmello/inquire/pull/181). ### Fixes diff --git a/inquire/src/prompts/dateselect/mod.rs b/inquire/src/prompts/dateselect/mod.rs index 515b4457..8d72c671 100644 --- a/inquire/src/prompts/dateselect/mod.rs +++ b/inquire/src/prompts/dateselect/mod.rs @@ -81,6 +81,9 @@ pub struct DateSelect<'a> { /// Max date allowed to be selected. pub max_date: Option, + /// Dates to mark with special styling. + pub marked_dates: &'a [NaiveDate], + /// Help message to be presented to the user. pub help_message: Option<&'a str>, @@ -133,6 +136,9 @@ impl<'a> DateSelect<'a> { /// Default max date. pub const DEFAULT_MAX_DATE: Option = None; + /// Default marked dates. + pub const DEFAULT_MARKED_DATES: &'a [NaiveDate] = &[]; + /// Creates a [DateSelect] with the provided message, along with default configuration values. pub fn new(message: &'a str) -> Self { Self { @@ -140,6 +146,7 @@ impl<'a> DateSelect<'a> { starting_date: get_current_date(), min_date: Self::DEFAULT_MIN_DATE, max_date: Self::DEFAULT_MAX_DATE, + marked_dates: Self::DEFAULT_MARKED_DATES, help_message: Self::DEFAULT_HELP_MESSAGE, vim_mode: Self::DEFAULT_VIM_MODE, formatter: Self::DEFAULT_FORMATTER, @@ -184,6 +191,12 @@ impl<'a> DateSelect<'a> { self } + /// Sets the marked dates. + pub fn with_marked_dates(mut self, marked_dates: &'a [NaiveDate]) -> Self { + self.marked_dates = marked_dates; + self + } + /// Sets the starting date. Equivalent to [DateSelect::with_default](DateSelect::with_default). pub fn with_starting_date(mut self, starting_date: NaiveDate) -> Self { self.starting_date = starting_date; diff --git a/inquire/src/prompts/dateselect/prompt.rs b/inquire/src/prompts/dateselect/prompt.rs index 75a1eb77..2431e256 100644 --- a/inquire/src/prompts/dateselect/prompt.rs +++ b/inquire/src/prompts/dateselect/prompt.rs @@ -24,6 +24,7 @@ pub struct DateSelectPrompt<'a> { help_message: Option<&'a str>, formatter: DateFormatter<'a>, validators: Vec>, + marked_dates: &'a [NaiveDate], error: Option, } @@ -51,6 +52,7 @@ impl<'a> DateSelectPrompt<'a> { help_message: so.help_message, formatter: so.formatter, validators: so.validators, + marked_dates: so.marked_dates, error: None, }) } @@ -180,6 +182,7 @@ where self.current_date, self.config.min_date, self.config.max_date, + self.marked_dates, )?; if let Some(help_message) = self.help_message { diff --git a/inquire/src/ui/backend.rs b/inquire/src/ui/backend.rs index 7b950899..53da616d 100644 --- a/inquire/src/ui/backend.rs +++ b/inquire/src/ui/backend.rs @@ -595,6 +595,7 @@ pub mod date { selected_date: chrono::NaiveDate, min_date: Option, max_date: Option, + marked_dates: &[chrono::NaiveDate], ) -> Result<()>; } @@ -617,6 +618,7 @@ pub mod date { selected_date: chrono::NaiveDate, min_date: Option, max_date: Option, + marked_dates: &[chrono::NaiveDate], ) -> Result<()> { macro_rules! write_prefix { () => {{ @@ -695,6 +697,8 @@ pub mod date { } } else if date_it == today { style_sheet = self.render_config.calendar.today_date; + } else if marked_dates.contains(&date_it) { + style_sheet = self.render_config.calendar.marked_date; } else if date_it.month() != month.number_from_month() { style_sheet = self.render_config.calendar.different_month_date; } diff --git a/inquire/src/ui/render_config.rs b/inquire/src/ui/render_config.rs index 30d72042..b775f088 100644 --- a/inquire/src/ui/render_config.rs +++ b/inquire/src/ui/render_config.rs @@ -433,6 +433,8 @@ impl<'a> ErrorMessageRenderConfig<'a> { pub mod calendar { //! Module containing additional render config for date prompts. + use crate::ui::Attributes; + use super::{Color, StyleSheet, Styled}; /// Calendar configuration for error messages. @@ -467,6 +469,9 @@ pub mod calendar { /// Style sheet for dates that can not be selected due to the /// min/max settings. pub unavailable_date: StyleSheet, + + /// Style sheet for marked dates + pub marked_date: StyleSheet, } impl<'a> CalendarRenderConfig<'a> { @@ -480,6 +485,7 @@ pub mod calendar { today_date: StyleSheet::empty(), different_month_date: StyleSheet::empty(), unavailable_date: StyleSheet::empty(), + marked_date: StyleSheet::empty(), } } @@ -497,6 +503,9 @@ pub mod calendar { today_date: StyleSheet::empty().with_fg(Color::LightGreen), different_month_date: StyleSheet::empty().with_fg(Color::DarkGrey), unavailable_date: StyleSheet::empty().with_fg(Color::DarkGrey), + marked_date: StyleSheet::empty() + .with_attr(Attributes::BOLD) + .with_fg(Color::DarkGreen), } }