use std::fmt::Display;
use clap::{ArgAction, Parser, ValueEnum};
use crate::{
config::extended::OutputDestination,
textbuf::{alphabet, regexes},
ui, Error, Result,
};
#[derive(Parser, Debug)]
#[clap(author, about, version)]
pub struct Config {
#[arg(
short = 'k',
long,
default_value = "dvorak",
value_parser(alphabet::parse_alphabet)
)]
pub alphabet: alphabet::Alphabet,
#[arg(short = 'A', long = "all-patterns")]
pub use_all_patterns: bool,
#[arg(
short = 'x',
long = "pattern-name",
value_parser(regexes::parse_pattern_name)
)]
pub named_patterns: Vec<regexes::NamedPattern>,
#[arg(short = 'X', long)]
pub custom_patterns: Vec<String>,
#[arg(short, long, action = ArgAction::SetTrue)]
pub reverse: bool,
#[arg(short, long, action = ArgAction::SetTrue)]
pub unique_hint: bool,
#[arg(short = 'w', long, action = ArgAction::SetTrue)]
pub focus_wrap_around: bool,
#[command(flatten)]
pub colors: ui::colors::UiColors,
#[arg(long, value_enum, default_value_t = ui::HintAlignment::Leading)]
pub hint_alignment: ui::HintAlignment,
#[arg(short = 's', long = "hint-style", rename_all = "lowercase", value_enum)]
pub hint_style_arg: Option<HintStyleArg>,
#[clap(
long,
// default_value_t = HintSurroundingsArg{open: '{', close: '}'},
default_value = "{}",
value_parser(try_parse_chars)
)]
pub hint_surroundings: HintSurroundingsArg,
#[arg(value_enum, long, rename_all = "kebab-case", default_value = "tmux")]
pub default_output: OutputDestination,
#[arg(short = 'm', long, action = ArgAction::SetTrue)]
pub multi_select: bool,
#[arg(short = 'S', long, default_value = " ")]
pub separator: String,
}
#[derive(Debug, Clone, ValueEnum)]
pub enum HintStyleArg {
Bold,
Italic,
Underline,
Surround,
}
#[derive(Debug, Clone)]
pub struct HintSurroundingsArg {
pub open: char,
pub close: char,
}
impl Display for HintSurroundingsArg {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
write!(f, "{}{}", self.open, self.close)
}
}
pub(crate) fn try_parse_chars(src: &str) -> Result<HintSurroundingsArg> {
if src.chars().count() != 2 {
return Err(Error::ExpectedSurroundingPair);
}
let chars: Vec<char> = src.chars().collect();
Ok(HintSurroundingsArg {
open: chars[0],
close: chars[1],
})
}
impl Config {
pub fn hint_style(&self) -> Option<ui::HintStyle> {
match &self.hint_style_arg {
None => None,
Some(style) => match style {
HintStyleArg::Bold => Some(ui::HintStyle::Bold),
HintStyleArg::Italic => Some(ui::HintStyle::Italic),
HintStyleArg::Underline => Some(ui::HintStyle::Underline),
HintStyleArg::Surround => {
let HintSurroundingsArg { open, close } = self.hint_surroundings;
Some(ui::HintStyle::Surround(open, close))
}
},
}
}
}