From 3b6987e4ccf2bbd23bd26a158cd87eb24ff74bfa Mon Sep 17 00:00:00 2001 From: Jeremy Wall Date: Sun, 6 Mar 2022 20:34:20 -0500 Subject: [PATCH] Skeleton for a tabbed component --- web/src/components/mod.rs | 2 ++ web/src/components/shopping.rs | 38 ++++------------------------------ web/src/components/tabs.rs | 38 ++++++++++++++++++++++++++++++++++ web/src/pages/cook.rs | 10 +++++++-- web/src/pages/inventory.rs | 10 +++++++-- web/src/pages/mod.rs | 18 ++++++++-------- web/src/pages/plan.rs | 20 +++++++++++------- 7 files changed, 82 insertions(+), 54 deletions(-) create mode 100644 web/src/components/tabs.rs diff --git a/web/src/components/mod.rs b/web/src/components/mod.rs index f0020fc..e39e28b 100644 --- a/web/src/components/mod.rs +++ b/web/src/components/mod.rs @@ -15,8 +15,10 @@ pub mod header; pub mod recipe; pub mod root; pub mod shopping; +pub mod tabs; pub use header::*; pub use recipe::*; pub use root::*; pub use shopping::*; +pub use tabs::*; diff --git a/web/src/components/shopping.rs b/web/src/components/shopping.rs index f43c2bc..8d95172 100644 --- a/web/src/components/shopping.rs +++ b/web/src/components/shopping.rs @@ -11,7 +11,7 @@ // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. -use crate::{app_state::*, components::Recipe, service::AppService}; +use crate::{components::Recipe, service::AppService}; use crate::{console_error, console_log}; use std::collections::HashMap; use std::{ @@ -49,7 +49,7 @@ fn recipe_selection(props: RecipeCheckBoxProps) -> View { } #[component(RecipeSelector)] -pub fn recipe_selector(page_state: crate::pages::PageState) -> View { +pub fn recipe_selector() -> View { let app_service = use_context::(); let rows = create_memo(cloned!(app_service => move || { let mut rows = Vec::new(); @@ -92,17 +92,11 @@ pub fn recipe_selector(page_state: crate::pages::PageState) -> View { }).collect() )) } - input(type="button", value="Inventory", on:click=cloned!((page_state) => move |_| { - page_state.route.set(AppRoutes::Inventory); - })) - input(type="button", value="Cook", class="no-print", on:click=cloned!((page_state) => move |_| { - page_state.route.set(AppRoutes::Cook); - })) } } #[component(ShoppingList)] -pub fn shopping_list(page_state: crate::pages::PageState) -> View { +pub fn shopping_list() -> View { let app_service = use_context::(); let filtered_keys = Signal::new(HashSet::new()); let ingredients_map = Signal::new(BTreeMap::new()); @@ -166,17 +160,11 @@ pub fn shopping_list(page_state: crate::pages::PageState) -> View { modified_amts.set(HashMap::new()); })) (table_view.get().as_ref().clone()) - input(type="button", value="Plan", class="no-print", on:click=cloned!((page_state) => move |_| { - page_state.route.set(AppRoutes::Plan); - })) - input(type="button", value="Cook", class="no-print", on:click=cloned!((page_state) => move |_| { - page_state.route.set(AppRoutes::Cook); - })) } } #[component(RecipeList)] -pub fn recipe_list(page_state: crate::pages::PageState) -> View { +pub fn recipe_list() -> View { let app_service = use_context::(); let menu_list = create_memo(move || app_service.get_menu_list()); view! { @@ -192,23 +180,5 @@ pub fn recipe_list(page_state: crate::pages::PageState) -> View { } } }) - input(type="button", value="Inventory", class="no-print", on:click=cloned!((page_state) => move |_| { - page_state.route.set(AppRoutes::Inventory); - })) - input(type="button", value="Cook", class="no-print", on:click=cloned!((page_state) => move |_| { - page_state.route.set(AppRoutes::Cook); - })) - } -} - -#[component(MealPlan)] -pub fn meal_plan() -> View { - view! { - h1 { - "Select your recipes" - } - //RecipeSelector() - //ShoppingList() - //RecipeList() } } diff --git a/web/src/components/tabs.rs b/web/src/components/tabs.rs new file mode 100644 index 0000000..93e8f35 --- /dev/null +++ b/web/src/components/tabs.rs @@ -0,0 +1,38 @@ +// Copyright 2022 Jeremy Wall +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +use sycamore::prelude::*; + +use crate::app_state::AppRoutes; + +#[derive(Clone)] +pub struct TabState { + pub route: Signal, + pub inner: View, +} + +#[component(TabbedView)] +pub fn tabbed_view(state: TabState) -> View { + cloned!((state) => view! { + input(type="button", value="Plan", class="no-print", on:click=cloned!((state) => move |_| { + state.route.set(AppRoutes::Plan); + })) + input(type="button", value="Inventory", class="no-print", on:click=cloned!((state) => move |_| { + state.route.set(AppRoutes::Inventory); + })) + input(type="button", value="Cook", class="no-print", on:click=cloned!((state) => move |_| { + state.route.set(AppRoutes::Cook); + })) + (state.inner) + }) +} diff --git a/web/src/pages/cook.rs b/web/src/pages/cook.rs index ef177f0..f3d02f7 100644 --- a/web/src/pages/cook.rs +++ b/web/src/pages/cook.rs @@ -11,11 +11,12 @@ // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. -use crate::components::shopping::RecipeList; +use crate::components::{shopping::RecipeList, tabs::*}; use crate::pages::PageState; use sycamore::prelude::*; +#[derive(Clone)] pub struct CookPageProps { pub page_state: PageState, } @@ -23,6 +24,11 @@ pub struct CookPageProps { #[component(CookPage)] pub fn cook_page(props: CookPageProps) -> View { view! { - RecipeList(props.page_state) + TabbedView(TabState { + route: props.page_state.route.clone(), + inner: view! { + RecipeList() + }, + }) } } diff --git a/web/src/pages/inventory.rs b/web/src/pages/inventory.rs index 60bc857..2ed04af 100644 --- a/web/src/pages/inventory.rs +++ b/web/src/pages/inventory.rs @@ -11,11 +11,12 @@ // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. -use crate::components::shopping::ShoppingList; +use crate::components::{shopping::ShoppingList, tabs::*}; use crate::pages::PageState; use sycamore::prelude::*; +#[derive(Clone)] pub struct InventoryPageProps { pub page_state: PageState, } @@ -23,6 +24,11 @@ pub struct InventoryPageProps { #[component(InventoryPage)] pub fn inventory_page(props: InventoryPageProps) -> View { view! { - ShoppingList(props.page_state) + TabbedView(TabState { + route: props.page_state.route.clone(), + inner: view! { + ShoppingList() + }, + }) } } diff --git a/web/src/pages/mod.rs b/web/src/pages/mod.rs index f196f34..d8f49f1 100644 --- a/web/src/pages/mod.rs +++ b/web/src/pages/mod.rs @@ -1,11 +1,11 @@ // Copyright 2022 Jeremy Wall -// +// // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at -// +// // http://www.apache.org/licenses/LICENSE-2.0 -// +// // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -15,15 +15,15 @@ use sycamore::prelude::*; use crate::app_state::AppRoutes; -mod plan; -mod inventory; mod cook; +mod inventory; +mod plan; -pub use plan::*; -pub use inventory::*; pub use cook::*; +pub use inventory::*; +pub use plan::*; #[derive(Clone)] pub struct PageState { - pub route: Signal -} \ No newline at end of file + pub route: Signal, +} diff --git a/web/src/pages/plan.rs b/web/src/pages/plan.rs index 0274799..9742df0 100644 --- a/web/src/pages/plan.rs +++ b/web/src/pages/plan.rs @@ -1,28 +1,34 @@ // Copyright 2022 Jeremy Wall -// +// // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at -// +// // http://www.apache.org/licenses/LICENSE-2.0 -// +// // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. +use crate::components::{shopping::RecipeSelector, tabs::*}; use crate::pages::PageState; -use crate::components::RecipeSelector; use sycamore::prelude::*; +#[derive(Clone)] pub struct PlanPageProps { - pub page_state: PageState + pub page_state: PageState, } #[component(PlanPage)] pub fn plan_page(props: PlanPageProps) -> View { view! { - RecipeSelector(props.page_state) + TabbedView(TabState { + route: props.page_state.route.clone(), + inner: view! { + RecipeSelector() + }, + }) } -} \ No newline at end of file +}