diff --git a/Cargo.lock b/Cargo.lock index e802d51..0e64799 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1269,6 +1269,12 @@ version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "98de4bbd547a563b716d8dfa9aad1cb19bfab00f4fa09a6a4ed21dbcf44ce9c4" +[[package]] +name = "float_next_after" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8bf7cc16383c4b8d58b9905a8509f02926ce3058053c056376248d958c9df1e8" + [[package]] name = "fnv" version = "1.0.7" @@ -1831,6 +1837,21 @@ dependencies = [ "thiserror", ] +[[package]] +name = "iced_aw" +version = "0.11.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42e05df3019f20c6decea93d035b32a2afc7b329d89cc5a68cca097d0e0a1889" +dependencies = [ + "cfg-if", + "chrono", + "iced", + "iced_fonts", + "itertools", + "num-format", + "num-traits", +] + [[package]] name = "iced_core" version = "0.13.2" @@ -1851,6 +1872,15 @@ dependencies = [ "web-time", ] +[[package]] +name = "iced_fonts" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df7deb0800a850ee25c8a42559f72c0f249e577feb3aad37b9b65dc1e517e52a" +dependencies = [ + "iced_core", +] + [[package]] name = "iced_futures" version = "0.13.2" @@ -1894,6 +1924,7 @@ dependencies = [ "image", "kamadak-exif", "log", + "lyon_path", "once_cell", "raw-window-handle", "rustc-hash 2.0.0", @@ -1992,6 +2023,7 @@ dependencies = [ "iced_glyphon", "iced_graphics", "log", + "lyon", "once_cell", "resvg", "rustc-hash 2.0.0", @@ -2243,6 +2275,21 @@ version = "1.70.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7943c866cc5cd64cbc25b2e01621d07fa8eb2a1a23160ee81ce38704e97b8ecf" +[[package]] +name = "itertools" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "413ee7dfc52ee1a4949ceeb7dbc8a33f2d6c088194d9f922fb8318faf1f01186" +dependencies = [ + "either", +] + +[[package]] +name = "itoa" +version = "1.0.11" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49f1f14873335454500d59611f1cf4a4b0f786f9ac11f4312a78e4cf2566695b" + [[package]] name = "jni" version = "0.21.1" @@ -2351,6 +2398,7 @@ dependencies = [ "futures-util", "gio", "iced", + "iced_aw", "iced_futures", "iced_layershell", "iced_runtime", @@ -2483,6 +2531,58 @@ version = "0.12.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "234cf4f4a04dc1f57e24b96cc0cd600cf2af460d4161ac5ecdd0af8e1f3b2a38" +[[package]] +name = "lyon" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "91e7f9cda98b5430809e63ca5197b06c7d191bf7e26dfc467d5a3f0290e2a74f" +dependencies = [ + "lyon_algorithms", + "lyon_tessellation", +] + +[[package]] +name = "lyon_algorithms" +version = "1.0.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a3bca95f9a4955b3e4a821fbbcd5edfbd9be2a9a50bb5758173e5358bfb4c623" +dependencies = [ + "lyon_path", + "num-traits", +] + +[[package]] +name = "lyon_geom" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8af69edc087272df438b3ee436c4bb6d7c04aa8af665cfd398feae627dbd8570" +dependencies = [ + "arrayvec", + "euclid", + "num-traits", +] + +[[package]] +name = "lyon_path" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8e0b8aec2f58586f6eef237985b9a9b7cb3a3aff4417c575075cf95bf925252e" +dependencies = [ + "lyon_geom", + "num-traits", +] + +[[package]] +name = "lyon_tessellation" +version = "1.0.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "579d42360a4b09846eff2feef28f538696c7d6c7439bfa65874ff3cbe0951b2c" +dependencies = [ + "float_next_after", + "lyon_path", + "num-traits", +] + [[package]] name = "malloc_buf" version = "0.0.6" @@ -2674,6 +2774,16 @@ dependencies = [ "winapi", ] +[[package]] +name = "num-format" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a652d9771a63711fd3c3deb670acfbe5c30a4072e664d7a3bf5a9e1056ac72c3" +dependencies = [ + "arrayvec", + "itoa", +] + [[package]] name = "num-traits" version = "0.2.19" @@ -2681,6 +2791,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "071dfc062690e90b734c0b2273ce72ad0ffa95f0c74596bc250dcfd960262841" dependencies = [ "autocfg", + "libm", ] [[package]] diff --git a/lala_bar/Cargo.toml b/lala_bar/Cargo.toml index f454650..b97cc8e 100644 --- a/lala_bar/Cargo.toml +++ b/lala_bar/Cargo.toml @@ -44,3 +44,4 @@ iced_zbus_notification.workspace = true chrono = "0.4.38" async-trait.workspace = true tracing-journald = "0.3.0" +iced_aw = "0.11.0" diff --git a/lala_bar/src/main.rs b/lala_bar/src/main.rs index 2d8d6d2..1f7b3ec 100644 --- a/lala_bar/src/main.rs +++ b/lala_bar/src/main.rs @@ -5,6 +5,7 @@ use launcher::{LaunchMessage, Launcher}; use zbus_mpirs::ServiceInfo; use futures::channel::mpsc::Sender; +use iced_aw::date_picker::Date; use iced_layershell::reexport::{Anchor, Layer}; use iced_layershell::settings::{LayerShellSettings, Settings, StartMode}; use iced_layershell::to_layer_message; @@ -54,6 +55,7 @@ pub enum LaLaInfo { HiddenInfo, RightPanel, ErrorHappened(iced::window::Id), + Calendar, } #[to_layer_message(multi, info_name = "LaLaInfo")] @@ -87,6 +89,9 @@ pub enum Message { Ready(Sender), #[allow(unused)] LinkClicked(markdown::Url), + ToggleCalendar, + Cancel, + Submit(Date), } impl From for Message { diff --git a/lala_bar/src/music_bar.rs b/lala_bar/src/music_bar.rs index 2f66819..c475883 100644 --- a/lala_bar/src/music_bar.rs +++ b/lala_bar/src/music_bar.rs @@ -18,6 +18,7 @@ use iced::widget::{ text_input, Space, }; use iced::{executor, Alignment, Element, Font, Length, Task as Command, Theme}; +use iced_aw::{date_picker::Date, helpers::date_picker}; use iced_layershell::reexport::{Anchor, KeyboardInteractivity, Layer, NewLayerShellSettings}; use iced_layershell::MultiApplication; use iced_runtime::window::Action as WindowAction; @@ -48,8 +49,11 @@ pub struct LalaMusicBar { cached_hidden_notifications: Vec, sender: Option>, quite_mode: bool, - datetime: DateTime, + calendar_id: Option, + show_picker: bool, + date: Date, + is_calendar_open: bool, } impl LalaMusicBar { @@ -59,9 +63,9 @@ impl LalaMusicBar { let week = date.format("%A").to_string(); let time = self.datetime.time(); let time_info = time.format("%H:%M").to_string(); - + let week_btn = button(text(week.clone())).on_press(Message::ToggleCalendar); container(row![ - text(week), + week_btn, Space::with_width(5.), text(time_info), Space::with_width(5.), @@ -500,6 +504,10 @@ impl MultiApplication for LalaMusicBar { sender: None, quite_mode: false, datetime: Local::now(), + calendar_id: None, + show_picker: false, + date: Date::today(), + is_calendar_open: false, }, Command::batch(vec![ Command::done(Message::UpdateBalance), @@ -519,6 +527,8 @@ impl MultiApplication for LalaMusicBar { Some(LaLaInfo::HiddenInfo) } else if self.right_panel.is_some_and(|tid| tid == id) { Some(LaLaInfo::RightPanel) + } else if self.calendar_id.is_some_and(|tid| tid == id) { + Some(LaLaInfo::Calendar) } else { if let Some(info) = self.cached_notifications.get(&id) { return Some(LaLaInfo::Notify(Box::new(info.clone()))); @@ -547,6 +557,7 @@ impl MultiApplication for LalaMusicBar { self.hiddenid = Some(id); } LaLaInfo::RightPanel => self.right_panel = Some(id), + LaLaInfo::Calendar => self.calendar_id = Some(id), _ => unreachable!(), } } @@ -585,6 +596,36 @@ impl MultiApplication for LalaMusicBar { Message::RequestDBusInfoUpdate => { return Command::perform(get_metadata(), Message::DBusInfoUpdate) } + Message::ToggleCalendar => { + if self.is_calendar_open && self.calendar_id.is_some() { + self.is_calendar_open = false; + return iced_runtime::task::effect(Action::Window(WindowAction::Close( + self.calendar_id.unwrap(), + ))); + } else { + self.is_calendar_open = true; + return Command::done(Message::NewLayerShell { + settings: NewLayerShellSettings { + size: Some((400, 350)), + exclusive_zone: None, + anchor: Anchor::Right | Anchor::Bottom, + layer: Layer::Top, + margin: Some((10, 10, 10, 10)), + keyboard_interactivity: KeyboardInteractivity::Exclusive, + use_last_output: false, + }, + info: LaLaInfo::Calendar, + }); + } + } + + Message::Submit(date) => { + self.date = date; + self.show_picker = false; + } + Message::Cancel => { + self.show_picker = false; + } Message::RequestPlay => { if let Some(ref data) = self.service_data { if !data.can_play { @@ -1000,6 +1041,16 @@ impl MultiApplication for LalaMusicBar { return launcher.view(); } } + LaLaInfo::Calendar => { + let datepicker = date_picker( + true, + self.date, + button(text("Pick date")), + Message::Cancel, + Message::Submit, + ); + return column![datepicker].into(); + } LaLaInfo::Notify(unitwidgetinfo) => { let btnwidgets: Element = unitwidgetinfo.notify_button(self);