final version
[lp74.git] / src / main.rs
blob27cc3cd975204682749f4ede8abd9f7b88838881
1 #[macro_use] extern crate conrod;
2 extern crate find_folder;
3 extern crate piston_window;
4 extern crate graphics;
5 extern crate rand;
6 extern crate input;
7 extern crate image;
8 extern crate gfx_device_gl;
11 mod data;
12 use data::*;
14 mod display;
15 use display::*;
17 use conrod::Theme;
18 use conrod::color;
19 use conrod::events::input_provider::InputProvider;
20 use piston_window::{
21     Glyphs, OpenGL, PistonWindow, WindowSettings, UpdateEvent, EventLoop,
22     Window, ImageSize
24 use input::keyboard::Key;
25 use graphics::{Transformed, Image, DrawState};
27 fn handle_keys(ui: &Ui, d: &mut Data) {
28     let mut keys = ui.global_input.keys_just_pressed().collect::<Vec<_>>();
29     keys.dedup();
30     for k in keys {
31         match k {
32             Key::R => d.space.rotate(),
33             Key::E => d.space.set_pos_kind(PosKind::Edge),
34             Key::F => d.space.set_pos_kind(PosKind::Face),
35             Key::N => d.load_next_if_any(),
36             Key::P => d.load_prev_if_any(),
37             _ => match d.space.current {
38                 Pos::E((_, a)) => match k {
39                     Key::PageUp => d.space.inc_size(),
40                     Key::PageDown => d.space.dec_size(),
41                     _ => match a {
42                         Axis::X => match k {
43                             Key::Right => d.space.inc_pos(),
44                             Key::Left => d.space.dec_pos(),
45                             _ => {},
46                         },
47                         Axis::Y => match k {
48                             Key::Up => d.space.dec_pos(),
49                             Key::Down => d.space.inc_pos(),
50                             _ => {},
51                         },
52                         Axis::Z => match k {
53                             Key::Up => d.space.dec_pos(),
54                             Key::Down => d.space.inc_pos(),
55                             _ => {},
56                         },
57                     },
58                 },
59                 Pos::F((_, o)) => match k {
60                         Key::A => d.space.set_current_face_if_none(),
61                         _ => match o {
62                             Ori::Top => match k {
63                                 Key::Up => d.space.dec_pos(),
64                                 Key::Down => d.space.inc_pos(),
65                                 _ => {},
66                             },
67                             Ori::Back => match k {
68                                 Key::Down => d.space.dec_pos(),
69                                 Key::Up => d.space.inc_pos(),
70                                 _ => {},
71                             },
72                             Ori::Side => match k {
73                                 Key::Left => d.space.dec_pos(),
74                                 Key::Right => d.space.inc_pos(),
75                                 _ => {},
76                         },
77                     },
78                 },
79             },
80         };
81     }
84 fn main() {
85     let opengl = OpenGL::V3_2;
86     let mut window: PistonWindow = WindowSettings::new("LP74", [900, 600])
87         .opengl(opengl).exit_on_esc(true).build().unwrap();
89         let mut ui = {
90         let assets = find_folder::Search::KidsThenParents(3, 5)
91             .for_folder("assets").expect("Cannot find assets folder");
92         let font_path = assets.join("fonts/NotoSans/NotoSans-Regular.ttf");
93         let theme = Theme::default();
94         let glyph_cache = Glyphs::new(&font_path, window.factory.clone());
95         Ui::new(glyph_cache.unwrap(), theme)
96     };
98     window.set_ups(30);
99     window.set_max_fps(30);
101     let mut colors = Colors {
102         c1: color::rgb_bytes(57, 63, 63),
103         c2: color::rgb_bytes(30, 34, 34),
104         font: color::WHITE,
105         hide: color::rgba_bytes(57, 63, 63, 0.4),
106     };
108     let mut state = State::Design;
109     let mut data = Data::new();
111     while let Some(event) = window.next() {
112         let wsize = WSize {
113             header_h: 50.0,
114             side_w: 150.0,
115             w: window.size().width as f64,
116             h: window.size().height as f64
117         };
119         ui.handle_event(&event);
120         event.update(|_| ui.set_widgets(|ref mut uicell|
121                                         set_ui(uicell,
122                                                &mut state,
123                                                &mut data,
124                                                &mut colors,
125                                                &wsize)));
126         state = match state {
127             State::Visual(faces_map) => match faces_map {
128                 None => match generate_faces_map(&mut window, &data.space) {
129                         None => State::Err(String::from("Graphviz project's \"dot\" is not installed")),
130                         fmap_opt => State::Visual(fmap_opt),
131                 },
132                 Some(_) => State::Visual(faces_map),
133             },
134             State::Design => {
135                 handle_keys(&ui, &mut data);
136                 State::Design
137             },
138             State::Extensions => State::Err(String::from("No available extensions")),
139             s => s,
140         };
141         window.draw_2d(&event, |c, g| {
142             match &state {
143                 &State::Design => {
144                     if data.space.change != Change::None
145                         || data.history.change
146                         || ui.will_redraw() {
147                         data.history.change = false;
148                         piston_window::clear([0.0, 0.0, 0.0, 0.0], g);
149                         show_space(&data.space, &wsize, c, g);
150                         ui.needs_redraw();
151                     }
152                     data.save_if_changed();
153                 },
154                 &State::Visual(ref faces_map) => {
155                     if ui.will_redraw() {
156                         if let &Some(ref m) = faces_map {
157                             piston_window::clear([1.0, 1.0, 1.0, 1.0], g);
158                             let image = Image::new()
159                                 .rect(final_size(wsize,
160                                                  (m.get_width() as f64,
161                                                   (m.get_height()) as f64)));
162                             image.draw(m, &DrawState::default(),
163                                        c.transform.trans(0.0, 0.0), g);
164                             ui.needs_redraw();
165                         }
166                     }
167                 },
168                 &State::Extensions => {},
169                 &State::Err(_) => {},
170             }
171             ui.draw_if_changed(c, g);
172         });
173     }