paiagram/interface/tabs/
start.rs1use crate::interface::tabs::tree_view;
2
3use super::Tab;
4use bevy::ecs::system::{In, InMut};
5use bevy::log::prelude::*;
6use egui::{Frame, Label, Response, ScrollArea, Sense, Ui, UiBuilder, Vec2, vec2};
7use strum::IntoEnumIterator;
8use strum_macros::EnumIter;
9use egui_i18n::tr;
10
11#[derive(Debug, Default, Clone, Copy, EnumIter, PartialEq)]
12enum CurrentField {
13 #[default]
14 List,
15 About,
16 Misc,
17}
18
19impl CurrentField {
20 fn name(self) -> &'static str {
21 match self {
22 Self::List => "List",
23 Self::About => "About",
24 Self::Misc => "Misc",
25 }
26 }
27}
28
29#[derive(Debug, Default, Clone, Copy)]
30pub struct StartTab {
31 current_field: CurrentField,
32}
33
34impl PartialEq for StartTab {
35 fn eq(&self, _other: &Self) -> bool {
36 true
37 }
38}
39
40impl Tab for StartTab {
41 const NAME: &'static str = "Start";
42 fn main_display(&mut self, world: &mut bevy::ecs::world::World, ui: &mut Ui) {
43 match self.current_field {
44 CurrentField::List => {
45 if let Err(e) = world.run_system_cached_with(show_start, ui) {
46 error!("UI Error while displaying start page: {e}")
47 }
48 }
49 CurrentField::About => {
50 show_about(ui);
51 }
52 CurrentField::Misc => {}
53 }
54 }
55 fn title(&self) -> egui::WidgetText {
56 tr!("tab-start").into()
57 }
58 fn edit_display(&mut self, world: &mut bevy::ecs::world::World, ui: &mut Ui) {
59 if let Err(e) = world.run_system_cached_with(tree_view::show_tree_view, ui) {
60 error!("UI Error while displaying tree view: {e}")
61 }
62 }
63 fn display_display(&mut self, world: &mut bevy::ecs::world::World, ui: &mut Ui) {
64 for field in CurrentField::iter() {
65 ui.add_sized(vec2(ui.available_width(), 20.0), |ui: &mut Ui| {
66 ui.selectable_value(&mut self.current_field, field, field.name())
67 });
68 }
69 }
70 fn scroll_bars(&self) -> [bool; 2] {
71 [false, true]
72 }
73}
74
75fn show_start(InMut(ui): InMut<Ui>) {
76 const CARD_SPACING: f32 = 10.0;
77 ui.spacing_mut().item_spacing.x = CARD_SPACING;
78 ui.spacing_mut().item_spacing.y = CARD_SPACING;
79 ui.vertical_centered(|ui| {
80 ui.horizontal_wrapped(|ui| {
81 for _ in 0..=100 {
82 diagram_card(ui, "Create new diagram", None);
83 }
84 });
85 });
86}
87
88fn diagram_card(ui: &mut Ui, title: &str, image: Option<i32>) -> Response {
89 const CARD_WIDTH: f32 = 150.0;
91 const CARD_SIZE: Vec2 = Vec2 {
92 x: CARD_WIDTH,
93 y: CARD_WIDTH / 2.0 * 3.0,
94 };
95
96 let (rect, resp) = ui.allocate_exact_size(CARD_SIZE, Sense::click());
97 ui.scope_builder(UiBuilder::new().max_rect(rect).sense(resp.sense), |ui| {
98 let visuals = ui.style().interact(&ui.response());
99 let stroke = {
100 let mut a = visuals.bg_stroke;
101 a.width = 1.5;
102 a
103 };
104 Frame::new()
105 .fill(visuals.bg_fill)
106 .stroke(stroke)
107 .inner_margin(3)
108 .corner_radius(3)
109 .show(ui, |ui| {
110 ui.set_min_size(ui.available_size());
111 ui.with_layout(egui::Layout::bottom_up(egui::Align::Min), |ui| {
112 ui.add(Label::new(title).truncate())
113 });
114 });
115 })
116 .response
117}
118
119fn show_about(ui: &mut Ui) {
120 ui.vertical_centered(|ui| {
121 let max_width = (620.0f32).min(ui.available_width()) - 40.0;
122 ui.set_max_width(max_width);
123 ui.add_space(20.0);
124 ui.heading(tr!("program-name"));
125 ui.label(format!("Version: {}", env!("CARGO_PKG_VERSION")));
126 ui.monospace(format!("Revision: {}", git_version::git_version!()));
127 ui.add_space(10.0);
128 ui.separator();
129 ui.add_space(10.0);
130 ui.label("A high-performance transport timetable diagramming and analysis tool built with egui and Bevy.");
131 ui.add_space(20.0);
132
133 ui.collapsing("Authors", |ui| {
134 ui.label("• Lead Developer: Jeremy Gao");
135 ui.label("• Contributors: We don't have any yet");
136 });
137
138 ui.collapsing("Third-party Libraries", |ui| {
139 ui.label("Paiagram is made possible by the following open-source projects:");
140 ui.horizontal(|ui| {
141 ui.label("•");
142 ui.hyperlink_to("egui", "https://github.com/emilk/egui");
143 });
144 ui.horizontal(|ui| {
145 ui.label("•");
146 ui.hyperlink_to("Bevy Engine", "https://bevyengine.org/");
147 });
148 ui.horizontal(|ui| {
149 ui.label("•");
150 ui.hyperlink_to("Petgraph", "https://docs.rs/petgraph/latest/petgraph/");
151 });
152 ui.label("• Other Rust libraries. See cargo.toml and cargo.lock for a complete list of libraries used.");
153 });
154
155 ui.collapsing("License Information", |ui| {
156 ui.label("Paiagram is a free software. If you bought it, you're likely scammed :-(");
157 ScrollArea::vertical()
158 .max_height(400.0)
159 .show(ui, |ui| {
160 ui.monospace(include_str!("../../../LICENSE.md"));
161 });
162 });
163
164 ui.collapsing("Contact & Support", |ui| {
165 ui.label("• Bug Reports: We don't have one yet.");
166 ui.label("• Discussions: We don't have one yet.");
167 ui.horizontal(|ui| {
168 ui.label("• Email: ");
169 ui.hyperlink("mailto://wensimehrp@gmail.com");
170 });
171 });
172
173 ui.collapsing("Special Thanks", |ui| {
174 ui.label("• x.e.p., for showing how to make stuff");
175 ui.label("• Tantacurl, for showing how make accessible, reliable, and cool stuff");
176 });
177
178 ui.add_space(20.0);
179 ui.horizontal(|ui| {
180 ui.hyperlink_to("GitHub", "https://github.com/wensimehrp/Paiagram");
181 ui.label("•");
182 ui.hyperlink_to("Documentation", "https://wensimehrp.github.io/Paiagram");
183 });
184 ui.add_space(20.0);
185 });
186}