summaryrefslogtreecommitdiff
path: root/schist_desktop_gui/src/gui/components/balances_view
diff options
context:
space:
mode:
authorJoe Carstairs <me@joeac.net>2025-08-13 07:50:21 +0000
committerjoeac <me@joeac.net>2025-08-13 07:50:21 +0000
commitee3cd780e21260257b401c3f5cbababd9e27a15a (patch)
treeb0571649a1a1a7644dbc50183cc4c3a29966a963 /schist_desktop_gui/src/gui/components/balances_view
parent49342e8b553d5c92f1c043b3b0ce18bdf1c2cd44 (diff)
task-073
Co-authored-by: Joe Carstairs <jcarstairs@scottlogic.com> Reviewed-on: https://git.joeac.net/joeac/schist/pulls/1 Co-authored-by: Joe Carstairs <me@joeac.net> Co-committed-by: Joe Carstairs <me@joeac.net>
Diffstat (limited to 'schist_desktop_gui/src/gui/components/balances_view')
-rw-r--r--schist_desktop_gui/src/gui/components/balances_view/make_balances_view_greeting.rs9
-rw-r--r--schist_desktop_gui/src/gui/components/balances_view/update_balances_view.rs121
-rw-r--r--schist_desktop_gui/src/gui/components/balances_view/view_balances_view.rs22
-rw-r--r--schist_desktop_gui/src/gui/components/balances_view/view_group_names.rs143
4 files changed, 295 insertions, 0 deletions
diff --git a/schist_desktop_gui/src/gui/components/balances_view/make_balances_view_greeting.rs b/schist_desktop_gui/src/gui/components/balances_view/make_balances_view_greeting.rs
new file mode 100644
index 0000000..4926046
--- /dev/null
+++ b/schist_desktop_gui/src/gui/components/balances_view/make_balances_view_greeting.rs
@@ -0,0 +1,9 @@
+use crate::gui::components::text::Text;
+
+pub fn make_balances_view_greeting(group_name: Option<Text>) -> String {
+ if let Some(group_name) = group_name {
+ format!("Hello, {} balances!", group_name.content)
+ } else {
+ String::from("Hello, balances!")
+ }
+}
diff --git a/schist_desktop_gui/src/gui/components/balances_view/update_balances_view.rs b/schist_desktop_gui/src/gui/components/balances_view/update_balances_view.rs
new file mode 100644
index 0000000..100cbc9
--- /dev/null
+++ b/schist_desktop_gui/src/gui/components/balances_view/update_balances_view.rs
@@ -0,0 +1,121 @@
+use super::{
+ make_balances_view_greeting::make_balances_view_greeting, view_group_names::view_group_names,
+ Action, BalancesView, Message,
+};
+use crate::{
+ gui::components::{navigation, Text},
+ traits::Component,
+};
+
+pub fn update_balances_view(balances_view: &mut BalancesView, message: Message) -> Action {
+ match message {
+ Message::NavigationMessage(message) => update_navigation(balances_view, message),
+ Message::SetBuckets(buckets) => set_buckets(balances_view, buckets),
+ Message::SelectNextBucket => select_next_bucket(balances_view),
+ Message::SelectPrevBucket => select_prev_bucket(balances_view),
+ }
+}
+
+fn select_prev_bucket(balances_view: &mut BalancesView) -> Action {
+ match balances_view
+ .navigation
+ .update(navigation::Message::SelectPrev)
+ {
+ navigation::Action::SelectOption(option) => {
+ balances_view.greeting = make_balances_view_greeting(Some(option));
+ Action::None
+ }
+ navigation::Action::None => Action::None,
+ }
+}
+
+fn select_next_bucket(balances_view: &mut BalancesView) -> Action {
+ match balances_view
+ .navigation
+ .update(navigation::Message::SelectNext)
+ {
+ navigation::Action::SelectOption(option) => {
+ balances_view.greeting = make_balances_view_greeting(Some(option));
+ Action::None
+ }
+ navigation::Action::None => Action::None,
+ }
+}
+
+fn set_buckets(
+ balances_view: &mut BalancesView,
+ buckets: Vec<schist_models::bucket::Bucket>,
+) -> Action {
+ balances_view.buckets = buckets.clone();
+ match balances_view
+ .navigation
+ .update(navigation::Message::SetOptions(view_group_names(buckets)))
+ {
+ navigation::Action::SelectOption(option) => {
+ balances_view.greeting = make_balances_view_greeting(Some(option));
+ Action::None
+ }
+ navigation::Action::None => Action::None,
+ }
+}
+
+fn update_navigation(
+ balances_view: &mut BalancesView,
+ message: navigation::Message<Text>,
+) -> Action {
+ match balances_view.navigation.update(message) {
+ navigation::Action::SelectOption(group_name) => {
+ balances_view.greeting = make_balances_view_greeting(Some(group_name));
+ Action::None
+ }
+ navigation::Action::None => Action::None,
+ }
+}
+
+#[cfg(test)]
+mod test {
+ use schist_fakes::bucket::make_fake_bucket_builder;
+
+ use crate::{
+ gui::components::{
+ balances_view::{BalancesView, Message},
+ navigation,
+ },
+ traits::Component,
+ };
+
+ #[test]
+ fn update_navigation_updates_greeting() {
+ let groceries = make_fake_bucket_builder(0)
+ .group(String::from("normal expenses"))
+ .build()
+ .unwrap();
+ let fragrance = make_fake_bucket_builder(1)
+ .group(String::from("luxuries"))
+ .build()
+ .unwrap();
+ let maps = make_fake_bucket_builder(2)
+ .group(String::from("outdoors"))
+ .build()
+ .unwrap();
+ let buckets = vec![groceries, fragrance.clone(), maps];
+
+ let mut balances_view = BalancesView::new(buckets);
+ assert_eq!("Hello, normal expenses balances!", balances_view.greeting);
+
+ balances_view.update(Message::NavigationMessage(navigation::Message::SelectPrev));
+ assert_eq!("Hello, normal expenses balances!", balances_view.greeting);
+
+ balances_view.update(Message::NavigationMessage(navigation::Message::SelectPrev));
+ assert_eq!("Hello, normal expenses balances!", balances_view.greeting);
+
+ balances_view.update(Message::NavigationMessage(navigation::Message::SelectNext));
+ assert_eq!("Hello, luxuries balances!", balances_view.greeting);
+
+ balances_view.update(Message::NavigationMessage(navigation::Message::SelectNext));
+ assert_eq!("Hello, outdoors balances!", balances_view.greeting);
+
+ balances_view.update(Message::NavigationMessage(navigation::Message::SelectNext));
+ assert_eq!("Hello, outdoors balances!", balances_view.greeting);
+ }
+}
diff --git a/schist_desktop_gui/src/gui/components/balances_view/view_balances_view.rs b/schist_desktop_gui/src/gui/components/balances_view/view_balances_view.rs
new file mode 100644
index 0000000..e8a1e46
--- /dev/null
+++ b/schist_desktop_gui/src/gui/components/balances_view/view_balances_view.rs
@@ -0,0 +1,22 @@
+use iced::widget::{column, row, Container};
+use iced::{alignment, Element, Length};
+
+use crate::gui::components::{balances_view::Message, BalancesView};
+use crate::style::SPACING_LG;
+use crate::traits::Viewable;
+
+pub fn view_balances_view<'a>(balances_view: &'a BalancesView) -> Element<'a, Message> {
+ let navigation = balances_view
+ .navigation
+ .view()
+ .map(Message::NavigationMessage);
+ let main_content = column![iced::widget::text(balances_view.greeting.clone())];
+ row![
+ Container::new(navigation).width(Length::FillPortion(1)),
+ Container::new(main_content).width(Length::FillPortion(3)),
+ ]
+ .align_y(alignment::Vertical::Center)
+ .height(Length::Fill)
+ .spacing(SPACING_LG)
+ .into()
+}
diff --git a/schist_desktop_gui/src/gui/components/balances_view/view_group_names.rs b/schist_desktop_gui/src/gui/components/balances_view/view_group_names.rs
new file mode 100644
index 0000000..02900e9
--- /dev/null
+++ b/schist_desktop_gui/src/gui/components/balances_view/view_group_names.rs
@@ -0,0 +1,143 @@
+use itertools::Itertools;
+use schist_models::bucket::Bucket;
+
+use crate::gui::components::Text;
+
+pub fn view_group_names(buckets: Vec<Bucket>) -> Vec<Text> {
+ buckets
+ .iter()
+ .map(|b| b.group.clone())
+ .unique()
+ .map(Text::new)
+ .collect()
+}
+
+#[cfg(test)]
+mod test {
+ use schist_fakes::bucket::make_fake_bucket_builder;
+
+ use crate::gui::components::{balances_view::view_group_names::view_group_names, text::Text};
+
+ #[test]
+ fn preserves_order() {
+ let buckets = vec![
+ make_fake_bucket_builder(0)
+ .group(String::from("hydrogen"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(1)
+ .group(String::from("helium"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(2)
+ .group(String::from("lithium"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(3)
+ .group(String::from("beryllium"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(4)
+ .group(String::from("boron"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(5)
+ .group(String::from("carbon"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(6)
+ .group(String::from("nitrogen"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(7)
+ .group(String::from("oxygen"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("flourine"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("flourine"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("neon"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("magnesium"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("aluminium"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("silicon"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("phosphorus"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("sulphur"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("chlorine"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(8)
+ .group(String::from("argon"))
+ .build()
+ .unwrap(),
+ ];
+ let group_names = view_group_names(buckets);
+ assert_eq!(17, group_names.len());
+ assert_eq!(group_names[0], Text::new(String::from("hydrogen")));
+ assert_eq!(group_names[1], Text::new(String::from("helium")));
+ assert_eq!(group_names[2], Text::new(String::from("lithium")));
+ assert_eq!(group_names[3], Text::new(String::from("beryllium")));
+ assert_eq!(group_names[4], Text::new(String::from("boron")));
+ assert_eq!(group_names[5], Text::new(String::from("carbon")));
+ assert_eq!(group_names[6], Text::new(String::from("nitrogen")));
+ assert_eq!(group_names[7], Text::new(String::from("oxygen")));
+ assert_eq!(group_names[8], Text::new(String::from("flourine")));
+ assert_eq!(group_names[9], Text::new(String::from("neon")));
+ assert_eq!(group_names[10], Text::new(String::from("magnesium")));
+ assert_eq!(group_names[11], Text::new(String::from("aluminium")));
+ assert_eq!(group_names[12], Text::new(String::from("silicon")));
+ assert_eq!(group_names[13], Text::new(String::from("phosphorus")));
+ assert_eq!(group_names[14], Text::new(String::from("sulphur")));
+ assert_eq!(group_names[15], Text::new(String::from("chlorine")));
+ assert_eq!(group_names[16], Text::new(String::from("argon")));
+ }
+
+ #[test]
+ fn removes_duplicates() {
+ let buckets = vec![
+ make_fake_bucket_builder(0)
+ .group(String::from("hydrogen"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(1)
+ .group(String::from("helium"))
+ .build()
+ .unwrap(),
+ make_fake_bucket_builder(2)
+ .group(String::from("hydrogen"))
+ .build()
+ .unwrap(),
+ ];
+ let group_names = view_group_names(buckets);
+ assert_eq!(
+ vec![
+ Text::new(String::from("hydrogen")),
+ Text::new(String::from("helium")),
+ ],
+ group_names
+ );
+ }
+}