codeberg_cli/render/ui/
mod.rsuse anyhow::Context;
pub fn multi_fuzzy_select_with_key<T>(
items: &[T],
prompt: impl AsRef<str>,
is_selected: impl Fn(&T) -> bool,
f_display: impl Fn(&T) -> String,
) -> anyhow::Result<Vec<&T>> {
let already_selected = items
.iter()
.enumerate()
.filter(|(_, elem)| is_selected(elem))
.map(|(idx, _)| idx)
.collect::<Vec<_>>();
let displayed_items = items.iter().map(f_display).collect::<Vec<_>>();
let selected_indices = inquire::MultiSelect::new(prompt.as_ref(), displayed_items)
.with_default(&already_selected)
.raw_prompt()
.context("There's nothing to select from")?;
let selected_items = selected_indices
.into_iter()
.map(|raw| raw.index)
.filter_map(|idx| items.get(idx))
.collect::<Vec<_>>();
Ok(selected_items)
}
pub fn fuzzy_select_with_key<T>(
items: &[T],
prompt: impl AsRef<str>,
f_display: impl Fn(&T) -> String,
) -> anyhow::Result<&T> {
fuzzy_select_with_key_with_default(items, prompt, f_display, None)
}
pub fn fuzzy_select_with_key_with_default<T>(
items: &[T],
prompt: impl AsRef<str>,
f_display: impl Fn(&T) -> String,
default_index: Option<usize>,
) -> anyhow::Result<&T> {
if items.is_empty() {
anyhow::bail!("Nothing to select from. Aborting.")
}
let displayed_items = items.iter().map(f_display).collect::<Vec<_>>();
let mut dialogue = inquire::Select::new(prompt.as_ref(), displayed_items);
if let Some(index) = default_index {
dialogue = dialogue.with_starting_cursor(index);
}
let selected_index = dialogue.raw_prompt().map_err(anyhow::Error::from)?.index;
Ok(&items[selected_index])
}
pub fn confirm_with_prompt(prompt: &str) -> anyhow::Result<bool> {
inquire::Confirm::new(prompt)
.with_help_message("(y/n)?")
.prompt()
.map_err(anyhow::Error::from)
}