use crate::symbols::MacSymbol;
use egui::{Color32, Painter, Rect};
use std::borrow::Cow;
use std::sync::Arc;
pub type SegmentIconPainter<'a> = Arc<dyn Fn(&Painter, Rect, Color32) + 'a>;
pub type SegmentIconFn = fn(&Painter, Rect, Color32);
#[derive(Clone)]
pub enum SegmentContent<'a> {
Text(Cow<'a, str>),
Symbol(MacSymbol),
IconFn(SegmentIconFn),
Custom(SegmentIconPainter<'a>),
}
#[derive(Clone)]
pub struct SegmentItem<'a> {
pub(crate) content: SegmentContent<'a>,
pub(crate) width: Option<f32>,
pub(crate) enabled: bool,
pub(crate) has_menu: bool,
pub(crate) shows_menu_indicator: bool,
pub(crate) tooltip: Option<Cow<'a, str>>,
}
impl<'a> SegmentItem<'a> {
const fn with_content(content: SegmentContent<'a>) -> Self {
Self {
content,
width: None,
enabled: true,
has_menu: false,
shows_menu_indicator: false,
tooltip: None,
}
}
pub(crate) fn accessible_cow(&self) -> Option<Cow<'a, str>> {
match &self.content {
SegmentContent::Text(s) if !s.is_empty() => Some(s.clone()),
_ => self.tooltip.clone(),
}
}
pub fn new(label: impl Into<Cow<'a, str>>) -> Self {
Self::with_content(SegmentContent::Text(label.into()))
}
pub const fn from_symbol(symbol: MacSymbol) -> Self {
Self::with_content(SegmentContent::Symbol(symbol))
}
pub const fn from_icon_fn(painter: SegmentIconFn) -> Self {
Self::with_content(SegmentContent::IconFn(painter))
}
pub fn from_icon(painter: impl Fn(&Painter, Rect, Color32) + 'a) -> Self {
Self::with_content(SegmentContent::Custom(Arc::new(painter)))
}
pub const fn with_width(mut self, width: f32) -> Self {
self.width = Some(width);
self
}
pub const fn enabled(mut self, enabled: bool) -> Self {
self.enabled = enabled;
self
}
pub const fn with_menu(mut self, has_menu: bool) -> Self {
self.has_menu = has_menu;
self
}
pub const fn with_shows_menu_indicator(mut self, shows: bool) -> Self {
self.shows_menu_indicator = shows;
self
}
pub const fn with_submenu(mut self, enabled: bool) -> Self {
self.has_menu = enabled;
self.shows_menu_indicator = enabled;
self
}
pub fn with_tooltip(mut self, tooltip: impl Into<Cow<'a, str>>) -> Self {
self.tooltip = Some(tooltip.into());
self
}
}
impl<'a> From<&'a str> for SegmentItem<'a> {
fn from(s: &'a str) -> Self {
Self::new(s)
}
}
impl<'a> From<MacSymbol> for SegmentItem<'a> {
fn from(sym: MacSymbol) -> Self {
Self::from_symbol(sym)
}
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum SegmentMenuTrigger {
PressAndHold,
PullDown,
SecondaryClick,
Keyboard,
}
#[derive(Debug, Clone, Copy, PartialEq)]
pub struct SegmentEvent {
pub index: usize,
pub menu_trigger: Option<SegmentMenuTrigger>,
pub rect: Rect,
}
impl SegmentEvent {
#[inline]
pub const fn opens_menu(&self) -> bool {
self.menu_trigger.is_some()
}
}
pub type MacSegmentItem<'a> = SegmentItem<'a>;
pub type MacSegmentEvent = SegmentEvent;