1extern crate native_windows_gui2 as nwg;
8use nwg::NativeUi;
9
10#[derive(Default)]
11pub struct FlexBoxApp {
12 window: nwg::Window,
13 layout: nwg::FlexboxLayout,
14 button1: nwg::Button,
15 button2: nwg::Button,
16 button3: nwg::Button,
17}
18
19impl FlexBoxApp {
20 fn exit(&self) {
21 nwg::stop_thread_dispatch();
22 }
23}
24
25mod flexbox_app_ui {
29 use super::*;
30 use native_windows_gui2 as nwg;
31 use std::cell::RefCell;
32 use std::ops::Deref;
33 use std::rc::Rc;
34
35 pub struct FlexBoxAppUi {
36 inner: Rc<FlexBoxApp>,
37 default_handler: RefCell<Option<nwg::EventHandler>>,
38 }
39
40 impl nwg::NativeUi<FlexBoxAppUi> for FlexBoxApp {
41 fn build_ui(mut data: FlexBoxApp) -> Result<FlexBoxAppUi, nwg::NwgError> {
42 use nwg::Event as E;
43
44 nwg::Window::builder()
46 .size((500, 300))
47 .position((300, 300))
48 .title("Flexbox example")
49 .build(&mut data.window)?;
50
51 nwg::Button::builder()
52 .text("Btn 1")
53 .parent(&data.window)
54 .focus(true)
55 .build(&mut data.button1)?;
56
57 nwg::Button::builder()
58 .text("Btn 2")
59 .parent(&data.window)
60 .build(&mut data.button2)?;
61
62 nwg::Button::builder()
63 .text("Btn 3")
64 .parent(&data.window)
65 .build(&mut data.button3)?;
66
67 let ui = FlexBoxAppUi {
69 inner: Rc::new(data),
70 default_handler: Default::default(),
71 };
72
73 let evt_ui = Rc::downgrade(&ui.inner);
75 let handle_events = move |evt, _evt_data, handle| {
76 if let Some(evt_ui) = evt_ui.upgrade() {
77 match evt {
78 E::OnWindowClose => {
79 if &handle == &evt_ui.window {
80 FlexBoxApp::exit(&evt_ui);
81 }
82 }
83 _ => {}
84 }
85 }
86 };
87
88 *ui.default_handler.borrow_mut() = Some(nwg::full_bind_event_handler(
89 &ui.window.handle,
90 handle_events,
91 ));
92
93 use nwg::stretch::{
95 geometry::{Rect, Size},
96 style::{AlignSelf, Dimension as D, FlexDirection},
97 };
98 const FIFTY_PC: D = D::Percent(0.5);
99 const PT_10: D = D::Points(10.0);
100 const PT_5: D = D::Points(5.0);
101 const PADDING: Rect<D> = Rect {
102 start: PT_10,
103 end: PT_10,
104 top: PT_10,
105 bottom: PT_10,
106 };
107 const MARGIN: Rect<D> = Rect {
108 start: PT_5,
109 end: PT_5,
110 top: PT_5,
111 bottom: PT_5,
112 };
113
114 nwg::FlexboxLayout::builder()
115 .parent(&ui.window)
116 .flex_direction(FlexDirection::Row)
117 .padding(PADDING)
118 .child(&ui.button1)
119 .child_margin(MARGIN)
120 .child_max_size(Size {
121 width: D::Points(200.0),
122 height: D::Undefined,
123 })
124 .child_size(Size {
125 width: FIFTY_PC,
126 height: D::Auto,
127 })
128 .child(&ui.button2)
129 .child_margin(MARGIN)
130 .child_align_self(AlignSelf::FlexEnd)
131 .child_size(Size {
132 width: D::Percent(0.25),
133 height: FIFTY_PC,
134 })
135 .child(&ui.button3)
136 .child_margin(MARGIN)
137 .child_flex_grow(2.0)
138 .child_size(Size {
139 width: D::Auto,
140 height: D::Auto,
141 })
142 .build(&ui.layout)?;
143
144 return Ok(ui);
145 }
146 }
147
148 impl Drop for FlexBoxAppUi {
149 fn drop(&mut self) {
151 let handler = self.default_handler.borrow();
152 if handler.is_some() {
153 nwg::unbind_event_handler(handler.as_ref().unwrap());
154 }
155 }
156 }
157
158 impl Deref for FlexBoxAppUi {
159 type Target = FlexBoxApp;
160
161 fn deref(&self) -> &FlexBoxApp {
162 &self.inner
163 }
164 }
165}
166
167fn main() {
168 nwg::init().expect("Failed to init Native Windows GUI");
169 nwg::Font::set_global_family("Segoe UI").expect("Failed to set default font");
170
171 let _ui = FlexBoxApp::build_ui(Default::default()).expect("Failed to build UI");
172
173 nwg::dispatch_thread_events();
174}