1use crate::{enums, prelude::*};
2use floui_sys;
3use std::sync::Arc;
4
5#[derive(Clone)]
7pub struct Button {
8 inner: Arc<*mut floui_sys::CButton>,
9}
10
11unsafe impl Sync for Button {}
12unsafe impl Send for Button {}
13
14unsafe impl WidgetExt for Button {
15 fn inner(&self) -> *mut floui_sys::CWidget {
16 *self.inner as _
17 }
18 fn from_widget_ptr(ptr: *mut floui_sys::CWidget) -> Self {
19 Self {
20 inner: Arc::new(ptr as _),
21 }
22 }
23}
24
25impl Button {
26 pub fn new(label: &str) -> Self {
28 let label = std::ffi::CString::new(label).unwrap();
29 let inner = unsafe { Arc::new(floui_sys::CButton_new(label.as_ptr())) };
30 Self { inner }
31 }
32
33 pub fn action<F: 'static + FnMut(&Self)>(self, cb: F) -> Self {
35 unsafe {
36 unsafe extern "C" fn shim(
37 wid: *mut floui_sys::CWidget,
38 data: *mut std::os::raw::c_void,
39 ) {
40 let wid = Button::from_widget_ptr(wid as *mut _);
41 let a = data as *mut Box<dyn FnMut(&Button)>;
42 let f: &mut (dyn FnMut(&Button)) = &mut **a;
43 let _ = std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| f(&wid)));
44 }
45 let a: *mut Box<dyn FnMut(&Self)> = Box::into_raw(Box::new(Box::new(cb)));
46 let data: *mut std::os::raw::c_void = a as *mut std::os::raw::c_void;
47 let callback: floui_sys::CFlouiCallback = Some(shim);
48 floui_sys::CButton_action(*self.inner, callback, data);
49 }
50 self
51 }
52
53 pub fn filled(self) -> Self {
55 unsafe { floui_sys::CButton_filled(*self.inner) }
56 self
57 }
58
59 pub fn foreground(self, col: enums::Color) -> Self {
61 unsafe { floui_sys::CButton_foreground(*self.inner, col.0) }
62 self
63 }
64}
65
66#[derive(Clone)]
68pub struct Toggle {
69 inner: Arc<*mut floui_sys::CToggle>,
70}
71
72unsafe impl Sync for Toggle {}
73unsafe impl Send for Toggle {}
74
75unsafe impl WidgetExt for Toggle {
76 fn inner(&self) -> *mut floui_sys::CWidget {
77 *self.inner as _
78 }
79 fn from_widget_ptr(ptr: *mut floui_sys::CWidget) -> Self {
80 Self {
81 inner: Arc::new(ptr as _),
82 }
83 }
84}
85
86impl Toggle {
87 pub fn new(label: &str) -> Self {
89 let label = std::ffi::CString::new(label).unwrap();
90 let inner = unsafe { Arc::new(floui_sys::CToggle_new(label.as_ptr())) };
91 Self { inner }
92 }
93
94 pub fn action<F: 'static + FnMut(&Self)>(self, cb: F) -> Self {
96 unsafe {
97 unsafe extern "C" fn shim(
98 wid: *mut floui_sys::CWidget,
99 data: *mut std::os::raw::c_void,
100 ) {
101 let wid = Toggle::from_widget_ptr(wid as *mut _);
102 let a = data as *mut Box<dyn FnMut(&Toggle)>;
103 let f: &mut (dyn FnMut(&Toggle)) = &mut **a;
104 let _ = std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| f(&wid)));
105 }
106 let a: *mut Box<dyn FnMut(&Self)> = Box::into_raw(Box::new(Box::new(cb)));
107 let data: *mut std::os::raw::c_void = a as *mut std::os::raw::c_void;
108 let callback: floui_sys::CFlouiCallback = Some(shim);
109 floui_sys::CToggle_action(*self.inner, callback, data);
110 }
111 self
112 }
113
114 pub fn foreground(self, col: enums::Color) -> Self {
116 unsafe { floui_sys::CToggle_foreground(*self.inner, col.0) }
117 self
118 }
119
120 pub fn set_value(&self, val: bool) {
122 unsafe { floui_sys::CToggle_set_value(*self.inner, val as i32) }
123 }
124
125 pub fn with_value(self, val: bool) -> Self {
127 self.set_value(val);
128 self
129 }
130
131 pub fn value(&self) -> bool {
133 unsafe { floui_sys::CToggle_value(*self.inner) != 0 }
134 }
135}
136
137#[derive(Clone)]
139pub struct Check {
140 inner: Arc<*mut floui_sys::CCheck>,
141}
142
143unsafe impl Sync for Check {}
144unsafe impl Send for Check {}
145
146unsafe impl WidgetExt for Check {
147 fn inner(&self) -> *mut floui_sys::CWidget {
148 *self.inner as _
149 }
150 fn from_widget_ptr(ptr: *mut floui_sys::CWidget) -> Self {
151 Self {
152 inner: Arc::new(ptr as _),
153 }
154 }
155}
156
157impl Check {
158 pub fn new(label: &str) -> Self {
160 let label = std::ffi::CString::new(label).unwrap();
161 let inner = unsafe { Arc::new(floui_sys::CCheck_new(label.as_ptr())) };
162 Self { inner }
163 }
164
165 pub fn action<F: 'static + FnMut(&Self)>(self, cb: F) -> Self {
167 unsafe {
168 unsafe extern "C" fn shim(
169 wid: *mut floui_sys::CWidget,
170 data: *mut std::os::raw::c_void,
171 ) {
172 let wid = Check::from_widget_ptr(wid as *mut _);
173 let a = data as *mut Box<dyn FnMut(&Check)>;
174 let f: &mut (dyn FnMut(&Check)) = &mut **a;
175 let _ = std::panic::catch_unwind(std::panic::AssertUnwindSafe(|| f(&wid)));
176 }
177 let a: *mut Box<dyn FnMut(&Self)> = Box::into_raw(Box::new(Box::new(cb)));
178 let data: *mut std::os::raw::c_void = a as *mut std::os::raw::c_void;
179 let callback: floui_sys::CFlouiCallback = Some(shim);
180 floui_sys::CCheck_action(*self.inner, callback, data);
181 }
182 self
183 }
184
185 pub fn foreground(self, col: enums::Color) -> Self {
187 unsafe { floui_sys::CCheck_foreground(*self.inner, col.0) }
188 self
189 }
190
191 pub fn set_value(&self, val: bool) {
193 unsafe { floui_sys::CCheck_set_value(*self.inner, val as i32) }
194 }
195
196 pub fn with_value(self, val: bool) -> Self {
198 self.set_value(val);
199 self
200 }
201
202 pub fn value(&self) -> bool {
204 unsafe { floui_sys::CCheck_value(*self.inner) != 0 }
205 }
206}