Consolidate desktop controls with editable holidays and a running-window tray
This commit is contained in:
1 parent
9908dde9f8
commit
326465952a
55 files changed
+4207
-450
No files matched your search
@@ -1,4 +1,5 @@
|
||||
mod all_options;
|
||||
mod calendar_controls;
|
||||
mod connections;
|
||||
mod form_controls;
|
||||
mod navigation;
|
||||
@@ -66,6 +67,7 @@ fn main() -> cosmic::iced::Result {
|
||||
Some("bar") => Some(InitialPage::Bar),
|
||||
Some("appearance") => Some(InitialPage::Settings(Page::Appearance)),
|
||||
Some("general") => Some(InitialPage::Settings(Page::General)),
|
||||
Some("calendar") => Some(InitialPage::Settings(Page::Calendar)),
|
||||
Some("theme") => Some(InitialPage::Settings(Page::Theme)),
|
||||
Some("tray") => Some(InitialPage::Settings(Page::Tray)),
|
||||
Some("all-options") => Some(InitialPage::Settings(Page::Configuration)),
|
||||
@@ -134,6 +136,7 @@ enum Message {
|
||||
RowVisibility(&'static str, usize, bool),
|
||||
Search(String),
|
||||
Sidebar(bool),
|
||||
RevealNavigation,
|
||||
Change(Edit),
|
||||
PanelClearSelection,
|
||||
PanelPage(panel_controls::PanelPage),
|
||||
@@ -173,6 +176,8 @@ enum Message {
|
||||
LockPreviewStarted(Result<(), String>),
|
||||
WallpaperPicked(wallpaper_controls::Target, Result<Option<String>, String>),
|
||||
NewCommand(String),
|
||||
AddHoliday,
|
||||
CalendarFunction(calendar_controls::FunctionInput),
|
||||
AddCommand,
|
||||
AddSwipe(&'static str),
|
||||
Remove(String, usize),
|
||||
@@ -207,6 +212,7 @@ struct App {
|
||||
inputs: HashMap<String, String>,
|
||||
ranges: HashMap<String, f64>,
|
||||
new_command: String,
|
||||
calendar_editor: calendar_controls::FunctionEditor,
|
||||
font: cosmic::font::Font,
|
||||
native_palette: visuals::Palette,
|
||||
family_ids: std::sync::Arc<Vec<String>>,
|
||||
@@ -324,6 +330,7 @@ impl cosmic::Application for App {
|
||||
inputs: HashMap::new(),
|
||||
ranges: HashMap::new(),
|
||||
new_command: String::new(),
|
||||
calendar_editor: Default::default(),
|
||||
font,
|
||||
native_palette,
|
||||
gallery_focus: None,
|
||||
@@ -358,7 +365,10 @@ impl cosmic::Application for App {
|
||||
} else {
|
||||
Task::none()
|
||||
};
|
||||
let task = Task::batch([task, tray_apps]);
|
||||
let reveal =
|
||||
cosmic::iced::advanced::widget::operate(navigation::RevealRow::navigation(app.page))
|
||||
.map(cosmic::Action::App);
|
||||
let task = Task::batch([task, tray_apps, reveal]);
|
||||
let connections = if app.page == Page::Connections {
|
||||
app.refresh_connections()
|
||||
} else {
|
||||
@@ -460,6 +470,7 @@ impl cosmic::Application for App {
|
||||
|| !self.ranges.is_empty()
|
||||
|| !self.pending.is_empty()
|
||||
|| self.options.dirty()
|
||||
|| self.calendar_editor.dirty(&self.draft)
|
||||
{
|
||||
self.status =
|
||||
"Config changed externally · Reload when your edits are finished"
|
||||
@@ -469,6 +480,7 @@ impl cosmic::Application for App {
|
||||
&snapshot.doc,
|
||||
));
|
||||
self.options.reset(&snapshot);
|
||||
self.calendar_editor.refresh(&snapshot);
|
||||
self.current = snapshot.clone();
|
||||
self.draft = snapshot;
|
||||
self.family_sections = theme_controls::FamilySections::new(
|
||||
@@ -517,11 +529,21 @@ impl cosmic::Application for App {
|
||||
Message::Sidebar(open) => {
|
||||
self.sidebar_open = open;
|
||||
if open {
|
||||
return cosmic::iced::widget::operation::focus(widget::Id::new(
|
||||
"settings-search",
|
||||
));
|
||||
return Task::batch([
|
||||
cosmic::iced::widget::operation::focus(widget::Id::new("settings-search")),
|
||||
cosmic::iced::advanced::widget::operate(navigation::RevealRow::navigation(
|
||||
self.page,
|
||||
))
|
||||
.map(cosmic::Action::App),
|
||||
]);
|
||||
}
|
||||
}
|
||||
Message::RevealNavigation => {
|
||||
return cosmic::iced::advanced::widget::operate(navigation::RevealRow::navigation(
|
||||
self.page,
|
||||
))
|
||||
.map(cosmic::Action::App);
|
||||
}
|
||||
Message::Page(page) => {
|
||||
self.sidebar_open = false;
|
||||
if self.page == page && self.search.is_empty() {
|
||||
@@ -545,6 +567,13 @@ impl cosmic::Application for App {
|
||||
widget::Id::new("settings-content"),
|
||||
cosmic::iced::widget::scrollable::RelativeOffset::START.into(),
|
||||
);
|
||||
let reset = Task::batch([
|
||||
reset,
|
||||
cosmic::iced::advanced::widget::operate(navigation::RevealRow::navigation(
|
||||
page,
|
||||
))
|
||||
.map(cosmic::Action::App),
|
||||
]);
|
||||
if leaving {
|
||||
let cleanup = self.leave_connections();
|
||||
let load = match page {
|
||||
@@ -839,6 +868,7 @@ impl cosmic::Application for App {
|
||||
Ok(snapshot) => {
|
||||
ferese_config::locale::set(ferese_config::locale::from_document(&snapshot.doc));
|
||||
self.options.reset(&snapshot);
|
||||
self.calendar_editor.refresh(&snapshot);
|
||||
self.current = snapshot.clone();
|
||||
self.draft = snapshot;
|
||||
self.family_sections =
|
||||
@@ -1012,6 +1042,37 @@ impl cosmic::Application for App {
|
||||
return self.apply_wallpaper_edits(wallpaper_controls::restore_defaults());
|
||||
}
|
||||
Message::NewCommand(value) => self.new_command = value,
|
||||
Message::CalendarFunction(input) => return self.calendar_function_input(input),
|
||||
Message::AddHoliday if !self.saving => {
|
||||
let date = self
|
||||
.inputs
|
||||
.get("$holiday.date")
|
||||
.cloned()
|
||||
.unwrap_or_default()
|
||||
.trim()
|
||||
.to_owned();
|
||||
let name = self
|
||||
.inputs
|
||||
.get("$holiday.name")
|
||||
.cloned()
|
||||
.unwrap_or_default()
|
||||
.trim()
|
||||
.to_owned();
|
||||
let holiday = ferese_config::calendar::Holiday { date, name };
|
||||
if let Err(error) = holiday.validate() {
|
||||
self.error = Some(ferese_config::locale::translate(&error));
|
||||
} else {
|
||||
self.inputs.remove("$holiday.date");
|
||||
self.inputs.remove("$holiday.name");
|
||||
return self.change(Edit::Add(
|
||||
"status.calendar.custom_holidays".into(),
|
||||
vec![
|
||||
("date".into(), holiday.date.into()),
|
||||
("name".into(), holiday.name.into()),
|
||||
],
|
||||
));
|
||||
}
|
||||
}
|
||||
Message::AddCommand if !self.saving => match shlex::split(&self.new_command)
|
||||
.filter(|a| !a.is_empty())
|
||||
{
|
||||
@@ -1342,7 +1403,7 @@ mod tests {
|
||||
app.current = initial.clone();
|
||||
app.draft = initial.clone();
|
||||
app.saving = true; // An earlier save has not completed yet.
|
||||
let id = ItemId("network".into());
|
||||
let id = ItemId("audio".into());
|
||||
let _ = app.update(Message::PanelSelect(id.clone()));
|
||||
let _ = app.update(Message::PanelEdit(panel_edit::Action::Move(
|
||||
id.clone(),
|
||||
@@ -1366,11 +1427,9 @@ mod tests {
|
||||
let panels: Vec<ferese_panel::Panel> =
|
||||
serde_json::from_value(app.draft.item("panels").unwrap().clone()).unwrap();
|
||||
ferese_panel::validate(&panels).unwrap();
|
||||
assert_eq!(panels[0].start.groups[1].items[1].id, id);
|
||||
assert_eq!(
|
||||
panels[0].start.groups[1].items[1].overflow,
|
||||
ferese_panel::OverflowPolicy::Always
|
||||
);
|
||||
let moved = panels[0].start.groups[1].items.last().unwrap();
|
||||
assert_eq!(moved.id, id);
|
||||
assert_eq!(moved.overflow, ferese_panel::OverflowPolicy::Always);
|
||||
assert!(
|
||||
!panels[0].end.groups[0]
|
||||
.items
|
||||
@@ -1419,7 +1478,15 @@ mod tests {
|
||||
let _ = app.update(Message::PanelEdit(panel_edit::Action::Remove(id)));
|
||||
let _ = app.page_view();
|
||||
assert!(app.error.is_none());
|
||||
assert_eq!(app.draft.string("panels.0.end.groups.1.items.0.id", ""), "");
|
||||
assert!(
|
||||
!app.preview_panel()
|
||||
.unwrap()
|
||||
.end
|
||||
.groups
|
||||
.iter()
|
||||
.flat_map(|group| &group.items)
|
||||
.any(|item| item.kind == ferese_panel::ItemKind::Clock)
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -1509,7 +1576,7 @@ mod tests {
|
||||
panel_edit::Zone::Center,
|
||||
)));
|
||||
let _ = app.update(Message::PanelEdit(panel_edit::Action::Place(
|
||||
ItemId("network".into()),
|
||||
ItemId("audio".into()),
|
||||
panel_edit::Destination {
|
||||
zone: "end",
|
||||
group: GroupId("time".into()),
|
||||
@@ -1523,7 +1590,7 @@ mod tests {
|
||||
assert!(app.saving && app.pending.is_empty());
|
||||
assert_eq!(
|
||||
app.draft.string("panels.0.center.groups.1.items.0.id", ""),
|
||||
"network"
|
||||
"audio"
|
||||
);
|
||||
assert_eq!(
|
||||
app.draft.string("panels.0.center.groups.1.items.1.id", ""),
|
||||
|
||||
Reference in new issue
Block a user