diff --git a/Cargo.toml b/Cargo.toml index 4e896bc..b2f2349 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -15,8 +15,6 @@ web = ["dioxus/web"] desktop = ["dioxus/desktop"] mobile = ["dioxus/mobile"] -[profile] - [profile.wasm-dev] inherits = "dev" opt-level = 1 diff --git a/assets/dashboard.css b/assets/dashboard.css index 5ebd485..5f1afab 100644 --- a/assets/dashboard.css +++ b/assets/dashboard.css @@ -5,13 +5,14 @@ body { .container { display: grid; - grid-template-columns: minmax(200px, 1fr) 2fr 1.5fr; + grid-template-columns: 400px 2fr 1.6fr; gap: 20px; } #sidebar { background-color: #171b2e; - height: 100vh; + width: 400px; + height: 100%; border-top-right-radius: 20px; border-bottom-right-radius: 20px; } @@ -26,23 +27,29 @@ body { #top_container, #mid_container, #bottom_container { - background-color: #bb69f4; + box-sizing: border-box; + background-color: #171b2e; border-radius: 20px; width: 100%; + padding: 30px; } .right_container { display: grid; - grid-template-rows: 450px 450px; gap: 20px; padding-top: 20px; padding-right: 20px; + max-height: calc(100vh - 40px); } .right_box { - background-color: #bb69f4; + box-sizing: border-box; + padding: 30px; + background-color: #171b2e; border-radius: 20px; width: 100%; + height: 100%; + overflow: auto; } @media (max-width: 1000px) { @@ -57,6 +64,40 @@ body { display: none; height: 150px; border-radius: 20px; + } + + .right_container { + padding-top: 10px; + aspect-ratio: 1 / 1; width: 100%; } -} \ No newline at end of file +} + + +.line-chart { + width: 100%; + height: 100%; +} + + +.line-chart-svg { + width: 100%; + height: 100%; + display: block; +} + +.line-chart .fill { + background: linear-gradient(to right, red, yellow); + -webkit-mask: url(#svg-path); + mask: url(#svg-path); + -webkit-mask-repeat: no-repeat; + mask-repeat: no-repeat; + -webkit-mask-size: contain; + mask-size: contain; + -webkit-mask-position: center; + mask-position: center; +} + +.line-chart .line { + stroke-width: 1px; +} diff --git a/src/components/mod.rs b/src/components/mod.rs new file mode 100644 index 0000000..3a9c11f --- /dev/null +++ b/src/components/mod.rs @@ -0,0 +1,98 @@ +use dioxus::prelude::*; + +#[component] +pub fn LineChart( + data: Vec, + max: Option, + start_color: Option, + start_opacity: Option, + end_color: Option, + end_opacity: Option, +) -> Element { + let width = 300.0; + let height = 200.0; + let start_color = start_color.unwrap_or(0x4f46e5); + let start_opacity = start_opacity.unwrap_or(0.4); + let end_color = end_color.unwrap_or(0x4f46e5); + let end_opacity = end_opacity.unwrap_or(0.0); + + let max_y = max + .map(|v| v as f64) + .unwrap_or_else(|| *data.iter().max().unwrap_or(&100) as f64); + + let points: Vec<(f64, f64)> = data + .iter() + .enumerate() + .map(|(i, &y)| { + let x = i as f64 / (data.len() - 1).max(1) as f64 * width; + let y = height - (y as f64 / max_y * height); + (x, y) + }) + .collect(); + + let path_data = { + let mut d = format!("M {} {}", points[0].0, points[0].1); + for &(x, y) in &points[1..] { + d += &format!(" L {} {}", x, y); + } + d + }; + + let fill_path_data = { + let mut d = format!("M {} {}", points[0].0, height); + for &(x, y) in &points { + d += &format!(" L {} {}", x, y); + } + d += &format!(" L {} {}", points.last().unwrap().0, height); + d + " Z" + }; + + rsx! { + div { + class: "line-chart", + svg { + preserve_aspect_ratio: "none", + class: "line-chart-svg", + width: "{width}", + height: "{height}", + view_box: "0 0 {width} {height}", + xmlns: "http://www.w3.org/2000/svg", + + defs { + linearGradient { + id: "gradient-fill", + x1: "0", + y1: "0", + x2: "0", + y2: "1", + + stop { + offset: "0%", + stop_color: "#{start_color:06X}", + stop_opacity: "{start_opacity}", + } + stop { + offset: "100%", + stop_color: "#{end_color:06X}", + stop_opacity: "{end_opacity}", + } + } + } + + path { + class: "fill", + d: "{fill_path_data}", + fill: "url(#gradient-fill)" + } + + path { + class: "line", + d: "{path_data}", + fill: "none", + stroke: "#4f46e5", + stroke_width: "2" + } + } + } + } +} diff --git a/src/dashboard.rs b/src/dashboard.rs index 5903036..17ad561 100644 --- a/src/dashboard.rs +++ b/src/dashboard.rs @@ -1,5 +1,7 @@ use dioxus::prelude::*; +use crate::components::LineChart; + const DASHBOARD_CSS: Asset = asset!("/assets/dashboard.css"); #[component] @@ -14,13 +16,19 @@ pub fn Dashboard() -> Element { div { class: "left_container", div { id: "top_container" } - div { id: "mid_container" } + div { id: "mid_container", + LineChart { data: vec![90, 60, 70, 50], max: 170, start_opacity: 0.3 } + } div { id: "bottom_container" } } div { class: "right_container", - div { class: "right_box" } - div { class: "right_box" } + div { class: "right_box", + LineChart { data: vec![90, 60, 70, 50], max: 170, start_opacity: 0.3 } + } + div { class: "right_box", + LineChart { data: vec![90, 60, 70, 50], max: 170, start_opacity: 0.3 } + } } } } diff --git a/src/main.rs b/src/main.rs index e8121e4..06fcf32 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,6 +1,7 @@ mod backend; mod dashboard; mod login; +mod components; use dioxus::prelude::*;