commit 92776105b35cbe292973638e061220c68c32fcb5 Author: aOK Date: Tue Dec 12 15:44:16 2023 +0300 first commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..48c3ca4 --- /dev/null +++ b/.gitignore @@ -0,0 +1,3 @@ +/dist/ +/target/ +/Cargo.lock diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..5165811 --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,26 @@ +[package] +name = "simplestacknavigation" +version = "0.0.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[profile.small] +inherits = "release" +#debug = true +opt-level = 'z' # Optimize for size +lto = true # Enable link-time optimization +codegen-units = 1 # Reduce number of codegen units to increase optimizations +panic = 'abort' # Abort on panic +strip = true + +[profile.release] +opt-level = "s" +lto = true +codegen-units = 1 +panic = "abort" +strip = true + +[dependencies] +makepad-widgets = { version = "0.6.0" } +# makepad-widgets = { git = "https://github.com/makepad/makepad/", branch = "rik" } diff --git a/README.md b/README.md new file mode 100644 index 0000000..b85f4b2 --- /dev/null +++ b/README.md @@ -0,0 +1,34 @@ +# Makepad UI + +This template should help get you started developing with Makepad Rust UI. + +## Recommended IDE Setup + +[VS Code](https://code.visualstudio.com/) + [rust-analyzer](https://marketplace.visualstudio.com/items?itemName=rust-lang.rust-analyzer). + + +# Desktop in Debug Mode +cargo run + +# Desktop in Release Mode +cargo run --release + +# Desktop in small size +cargo run --profile=small + +# Android +cargo makepad android run --release + +# IOS Simulator +cargo makepad apple ios --org=my.test --app=makepad-template run-sim --release + +# IOS Device +cargo makepad apple ios --org-id=123456 --org=my.test --app=makepad-template run-device makepad-template --release + +# Cargo Check Builds +cargo makepad check install-toolchain +cargo makepad check all + +cargo makepad wasm install-toolchain +cargo makepad apple ios install-toolchain +cargo makepad android --abi=all install-toolchain \ No newline at end of file diff --git a/index.html b/index.html new file mode 100644 index 0000000..34f5eda --- /dev/null +++ b/index.html @@ -0,0 +1,34 @@ + + + + + + Makepad Template + + + + + + +
+
+ Loading.. +
+
+ + diff --git a/resources/icons/add_contact.svg b/resources/icons/add_contact.svg new file mode 100644 index 0000000..f9508de --- /dev/null +++ b/resources/icons/add_contact.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/icons/back.svg b/resources/icons/back.svg new file mode 100644 index 0000000..235235b --- /dev/null +++ b/resources/icons/back.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/icons/chat.svg b/resources/icons/chat.svg new file mode 100644 index 0000000..afec143 --- /dev/null +++ b/resources/icons/chat.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/icons/contacts.svg b/resources/icons/contacts.svg new file mode 100644 index 0000000..0109396 --- /dev/null +++ b/resources/icons/contacts.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/icons/discover.svg b/resources/icons/discover.svg new file mode 100644 index 0000000..32831e9 --- /dev/null +++ b/resources/icons/discover.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/icons/icon_home.svg b/resources/icons/icon_home.svg new file mode 100644 index 0000000..65ae1f8 --- /dev/null +++ b/resources/icons/icon_home.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/resources/icons/me.svg b/resources/icons/me.svg new file mode 100644 index 0000000..f9508de --- /dev/null +++ b/resources/icons/me.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/resources/icons/menu.svg b/resources/icons/menu.svg new file mode 100644 index 0000000..8d7f4ba --- /dev/null +++ b/resources/icons/menu.svg @@ -0,0 +1 @@ + ic_fluent_add_circle_28_regular Created with Sketch. \ No newline at end of file diff --git a/resources/icons/money.svg b/resources/icons/money.svg new file mode 100644 index 0000000..f5edd73 --- /dev/null +++ b/resources/icons/money.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/resources/icons/scan.svg b/resources/icons/scan.svg new file mode 100644 index 0000000..d1f3c12 --- /dev/null +++ b/resources/icons/scan.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/resources/icons/search.svg b/resources/icons/search.svg new file mode 100644 index 0000000..52f7f3f --- /dev/null +++ b/resources/icons/search.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/resources/makepad.png b/resources/makepad.png new file mode 100644 index 0000000..052f301 Binary files /dev/null and b/resources/makepad.png differ diff --git a/resources/makepad.svg b/resources/makepad.svg new file mode 100644 index 0000000..5a2c8ef --- /dev/null +++ b/resources/makepad.svg @@ -0,0 +1,42 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/resources/me.svg b/resources/me.svg new file mode 100644 index 0000000..f9508de --- /dev/null +++ b/resources/me.svg @@ -0,0 +1,4 @@ + + + + \ No newline at end of file diff --git a/src/api.rs b/src/api.rs new file mode 100644 index 0000000..38ae405 --- /dev/null +++ b/src/api.rs @@ -0,0 +1,244 @@ +use makepad_widgets::makepad_platform::{LiveId, live_id}; +use std::iter; + +#[derive(Clone, Debug)] +pub struct ChatEntry { + pub id: u64, + pub username: String, + pub avatar: LiveId, + pub latest_message: MessagePreview, + pub timestamp: String, +} +#[derive(Clone, Debug)] +pub struct Counter { + pub id: u64, + pub username: String, + pub counter: usize, + pub avatar: LiveId, + pub latest_message: MessagePreview, + pub timestamp: String, +} + +#[derive(Clone, Debug)] +pub enum MessagePreview { + Audio, + Image, + Video, + Text(String), +} + +impl MessagePreview { + pub fn text(&self) -> &str { + match self { + MessagePreview::Audio => "[Audio]", + MessagePreview::Image => "[Image]", + MessagePreview::Video => "[Video]", + MessagePreview::Text(text) => text, + } + } +} + +#[derive(Clone, Debug)] +pub enum MessageDirection { + Outgoing, + Incoming, +} + +#[derive(Clone, Debug)] +pub struct MessageEntry { + pub direction: MessageDirection, + pub chat_id: u64, + pub avatar: LiveId, + pub text: String, +} + +pub struct Db { + messages: Vec, + chats: Vec, + counts: Vec, +} + +impl Default for Db { + fn default() -> Self { + Self::new() + } +} + +impl Db { + pub fn new() -> Self { + let messages: Vec = (0..200) + .flat_map(|i| { + vec![ + MessageEntry { + direction: MessageDirection::Incoming, + avatar: live_id!(jorgebejar), + chat_id: (i * 2) % 50 + 1, + text: "体議速人幅触無持編聞組込".to_string(), + }, + MessageEntry { + direction: MessageDirection::Outgoing, + avatar: live_id!(rikarends), + chat_id: (i * 2) % 50 + 1, + text: "減活乗治外進".to_string(), + }, + MessageEntry { + direction: MessageDirection::Incoming, + avatar: live_id!(jorgebejar), + chat_id: (i * 2) % 50 + 1, + text: "福読併棋一御質慰".to_string(), + }, + MessageEntry { + direction: MessageDirection::Outgoing, + avatar: live_id!(rikarends), + chat_id: (i * 2) % 50 + 1, + text: "嶋可済政実玉全強無示餌".to_string(), + }, + MessageEntry { + direction: MessageDirection::Outgoing, + avatar: live_id!(johndoe), + chat_id: (i * 2) % 50 + 2, + text: "福読併棋一御質慰".to_string(), + }, + MessageEntry { + direction: MessageDirection::Incoming, + avatar: live_id!(julianmontesdeoca), + chat_id: (i * 2) % 50 + 2, + text: "消再野誰強心無嶋可済実玉全示餌".to_string(), + }, + MessageEntry { + direction: MessageDirection::Outgoing, + avatar: live_id!(johndoe), + chat_id: (i * 2) % 50 + 2, + text: "体議速人幅触無持編聞組込".to_string(), + }, + MessageEntry { + direction: MessageDirection::Incoming, + avatar: live_id!(julianmontesdeoca), + chat_id: (i * 2) % 50 + 2, + text: "減活乗治外進".to_string(), + }, + ] + }) + .collect(); + + Db { + messages, + chats: vec![ + ChatEntry { + id: 1, + username: "Olive Yew".to_string(), + avatar: live_id!(rikarends), + latest_message: MessagePreview::Text("Hi!".to_string()), + timestamp: "14:09".to_string(), + }, + ChatEntry { + id: 2, + username: "John Doe".to_string(), + avatar: live_id!(johndoe), + latest_message: MessagePreview::Image, + timestamp: "11:20".to_string(), + }, + ChatEntry { + id: 3, + username: "Peg Legge".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Audio, + timestamp: "friday".to_string(), + }, + ChatEntry { + id: 4, + username: "Barb Akew".to_string(), + avatar: live_id!(julianmontesdeoca), + latest_message: MessagePreview::Video, + timestamp: "friday".to_string(), + }, + ChatEntry { + id: 5, + username: "Chris P. Bacon".to_string(), + avatar: live_id!(edwardtan), + latest_message: MessagePreview::Text("thanks ed, see you there.".to_string()), + timestamp: "thursday".to_string(), + }, + ChatEntry { + id: 6, + username: "WeChat Team".to_string(), + avatar: live_id!(wechatteam), + latest_message: MessagePreview::Text("Welcome to WeChat!".to_string()), + timestamp: "18/07".to_string(), + }, + ChatEntry { + id: 7, + username: "Andrew Lin".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Text( + "Awesome, I'll make sure they know about it".to_string(), + ), + timestamp: "18/07".to_string(), + }, + ChatEntry { + id: 8, + username: "Christian Huxley".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Image, + timestamp: "15/07".to_string(), + }, + ChatEntry { + id: 9, + username: "Ana Leddie".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Image, + timestamp: "14/07".to_string(), + }, + ChatEntry { + id: 10, + username: "Adam Adler".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Video, + timestamp: "10/07".to_string(), + }, + ChatEntry { + id: 11, + username: "Gabriel Hayes".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Text("wow I haven't seen that".to_string()), + timestamp: "10/07".to_string(), + }, + ChatEntry { + id: 12, + username: "Eric Ford".to_string(), + avatar: live_id!(jorgebejar), + latest_message: MessagePreview::Text("Nice to see you here!".to_string()), + timestamp: "10/07".to_string(), + }, + ], + counts: vec![ + Counter { + id: 0, + username: "".to_string(), + count: 0, + avatar: live_id!(rikarends), + latest_message: MessagePreview::Text("Hi!".to_string()), + timestamp: "00:00".to_string(), + }], + } + } + + pub fn get_all_chats(&self) -> Vec { + iter::repeat(self.chats.clone()).take(50).flatten().collect() + } + + pub fn get_chat(&self, chat_id: u64) -> Option<&ChatEntry> { + self.chats.iter().find(|m| m.id == chat_id) + } + pub fn get_count(&self, chat_id: u64) -> Option<&ChatEntry> { + self.chats.iter().find(|m| m.id == chat_id) + } + + pub fn get_messages_by_chat_id(&self, chat_id: u64) -> Vec { + self.messages + .iter() + .filter(|m| m.chat_id == chat_id) + .cloned() + .collect() + } +} diff --git a/src/app.rs b/src/app.rs new file mode 100644 index 0000000..2bfc1bc --- /dev/null +++ b/src/app.rs @@ -0,0 +1,160 @@ +use crate::shared::stack_navigation::*; +use crate::shared::stack_view_action::StackViewAction; +use makepad_widgets::*; +use std::collections::HashMap; + +live_design!{ + import makepad_widgets::base::*; + import makepad_widgets::theme_desktop_dark::*; + + import crate::welcome::welcome_screen::WelcomeScreen + import crate::counter::counter_screen::CounterScreen + + import crate::shared::clickable_view::ClickableView + import crate::shared::stack_navigation::*; + + import crate::shared::styles::*; + + ICON_CHAT = dep("crate://self/resources/icons/chat.svg") + + + AppTab = { + width: Fit, + height: Fill, + align: {x: 0.0, y: 0.0} + draw_radio: { + radio_type: Tab, + color_active: #fff, + color_inactive: #fff, + } + draw_text: { + color_selected: #0b0, + color_unselected: #000, + color_unselected_hover: #111, + text_style: {} + } + } + + App = {{App}} { + + ui: { + show_bg: true + width: Fill, + height: Fill + draw_bg: { + fn pixel(self) -> vec4 { + return mix(#7, #3, self.pos.y); + } + } + body = { + navigation = { + root_view = { + width: Fill, + height: Fill, + padding: 0, align: {x: 0.0, y: 0.0}, spacing: 0., flow: Down + + application_pages = { + margin: 0.0, + padding: 0.0 + + welcome_frame = { visible: true } + } + } + my_counter_stack_view = { + header = { + content = { + title_container = { + title = { + text: "Counter" + } + } + } + } + {} + } + } + } + } + } +} + +app_main!(App); + +#[derive(Live)] +pub struct App { + #[live] ui: WidgetRef, + #[rust] counter: usize, + #[rust] navigation_destinations: HashMap, +} + +impl LiveHook for App { + fn before_live_design(cx: &mut Cx) { + crate::makepad_widgets::live_design(cx); + + // welcome + crate::welcome::welcome_screen::live_design(cx); + // counter + crate::counter::counter_screen::live_design(cx); + + // shared + crate::shared::styles::live_design(cx); + crate::shared::helpers::live_design(cx); + crate::shared::header::live_design(cx); + crate::shared::search_bar::live_design(cx); + crate::shared::custom_button::live_design(cx); + crate::shared::popup_menu::live_design(cx); + crate::shared::dropdown_menu::live_design(cx); + crate::shared::stack_navigation::live_design(cx); + crate::shared::clickable_view::live_design(cx); + } + fn after_new_from_doc(&mut self, _cx: &mut Cx) { + self.init_navigation_destinations(); + } +} + +impl App{ + fn init_navigation_destinations(&mut self) { + self.navigation_destinations = HashMap::new(); + self.navigation_destinations.insert(StackViewAction::ShowCounterScreen, live_id!(my_counter_stack_view)); + } + + async fn _do_network_request(_cx:CxRef, _ui:WidgetRef, _url:&str)->String{ + "".to_string() + } + +} + +impl AppMain for App{ + fn handle_event(&mut self, cx: &mut Cx, event: &Event) { + if let Event::Draw(event) = event { + return self.ui.draw_widget_all(&mut Cx2d::new(cx, event)); + } + let actions = self.ui.handle_widget_event(cx, event); + + self.ui.radio_button_set(ids!( + mobile_modes.tab1, + )) + .selected_to_visible( + cx, + &self.ui, + &actions, + ids!( + application_pages.welcome_frame, + ), + ); + let mut navigation = self.ui.stack_navigation(id!(navigation)); + navigation.handle_stack_view_actions( + cx, + &actions, + &self.navigation_destinations + ); + + + if self.ui.button(id!(button1)).clicked(&actions) { + log!("BUTTON CLICKED {}", self.counter); + self.counter += 1; + let label = self.ui.label(id!(label1)); + label.set_text_and_redraw(cx,&format!("Counter: {}", self.counter)); + } + } +} \ No newline at end of file diff --git a/src/counter/counter_screen.rs b/src/counter/counter_screen.rs new file mode 100644 index 0000000..cb49ae7 --- /dev/null +++ b/src/counter/counter_screen.rs @@ -0,0 +1,136 @@ +use crate::shared::clickable_view::*; +use crate::shared::stack_view_action::StackViewAction; +use makepad_widgets::widget::WidgetCache; +use makepad_widgets::*; + +live_design! { + import makepad_draw::shader::std::*; + import makepad_widgets::base::*; + import makepad_widgets::theme_desktop_dark::*; + + import crate::shared::helpers::FillerX; + import crate::shared::helpers::Divider; + import crate::shared::styles::*; + import crate::shared::clickable_view::ClickableView + // import crate::shared::header::HeaderDropDownMenu; + + + + Counter = {{Counter}} { + view: { + width: Fill, height: Fit + flow: Down, spacing: 10. + + show_bg: true, + draw_bg: { + color: #ddd + } + // {} + + body = { + + flow: Down, + spacing: 20, + align: { + x: 0.5, + y: 0.5 + }, + + avatar = { + source: (LOGO_MAKEPAD), + width: 300., height: 80. + } + button1 =