1use crate::Id;
16use crate::draw::DrawListMut;
17use crate::input::MouseCursor;
18use crate::internal::RawWrapper;
19use crate::string::UiBuffer;
20use crate::sys;
21use crate::texture::TextureRef;
22use std::cell::UnsafeCell;
23use std::ffi::CString;
24
25#[derive(Debug)]
27pub struct Ui {
28 buffer: UnsafeCell<UiBuffer>,
30}
31
32impl Ui {
33 #[doc(alias = "GetMainViewport")]
37 pub fn main_viewport(&self) -> &'static crate::platform_io::Viewport {
38 crate::platform_io::Viewport::main()
39 }
40 pub(crate) fn new() -> Self {
44 Ui {
45 buffer: UnsafeCell::new(UiBuffer::new(1024)),
46 }
47 }
48
49 #[doc(alias = "GetIO")]
51 pub fn io(&self) -> &crate::io::Io {
52 unsafe { &*(sys::igGetIO_Nil() as *const crate::io::Io) }
53 }
54
55 pub(crate) fn scratch_txt(&self, txt: impl AsRef<str>) -> *const std::os::raw::c_char {
57 unsafe {
58 let handle = &mut *self.buffer.get();
59 handle.scratch_txt(txt)
60 }
61 }
62
63 pub(crate) fn scratch_txt_opt(
65 &self,
66 txt: Option<impl AsRef<str>>,
67 ) -> *const std::os::raw::c_char {
68 unsafe {
69 let handle = &mut *self.buffer.get();
70 handle.scratch_txt_opt(txt)
71 }
72 }
73
74 pub(crate) fn scratch_txt_two(
76 &self,
77 txt_0: impl AsRef<str>,
78 txt_1: impl AsRef<str>,
79 ) -> (*const std::os::raw::c_char, *const std::os::raw::c_char) {
80 unsafe {
81 let handle = &mut *self.buffer.get();
82 handle.scratch_txt_two(txt_0, txt_1)
83 }
84 }
85
86 pub(crate) fn scratch_txt_with_opt(
88 &self,
89 txt_0: impl AsRef<str>,
90 txt_1: Option<impl AsRef<str>>,
91 ) -> (*const std::os::raw::c_char, *const std::os::raw::c_char) {
92 unsafe {
93 let handle = &mut *self.buffer.get();
94 handle.scratch_txt_with_opt(txt_0, txt_1)
95 }
96 }
97
98 pub(crate) fn scratch_buffer(&self) -> &UnsafeCell<UiBuffer> {
100 &self.buffer
101 }
102
103 #[doc(alias = "TextUnformatted")]
105 pub fn text<T: AsRef<str>>(&self, text: T) {
106 let s = text.as_ref();
107 unsafe {
108 let start = s.as_ptr();
109 let end = start.add(s.len());
110 crate::sys::igTextUnformatted(
111 start as *const std::os::raw::c_char,
112 end as *const std::os::raw::c_char,
113 );
114 }
115 }
116
117 #[doc(alias = "SetNextWindowViewport")]
122 pub fn set_next_window_viewport(&self, viewport_id: Id) {
123 unsafe { sys::igSetNextWindowViewport(viewport_id.into()) }
124 }
125
126 #[doc(alias = "GetID")]
131 pub fn get_id(&self, label: &str) -> Id {
132 let c = CString::new(label).expect("label contained null byte");
133 unsafe { Id::from(sys::igGetID_Str(c.as_ptr())) }
134 }
135
136 #[doc(alias = "GetWindowDrawList")]
138 pub fn get_window_draw_list(&self) -> DrawListMut<'_> {
139 DrawListMut::window(self)
140 }
141
142 #[doc(alias = "GetBackgroundDrawList")]
144 pub fn get_background_draw_list(&self) -> DrawListMut<'_> {
145 DrawListMut::background(self)
146 }
147
148 #[doc(alias = "GetForegroundDrawList")]
150 pub fn get_foreground_draw_list(&self) -> DrawListMut<'_> {
151 DrawListMut::foreground(self)
152 }
153
154 pub fn window(&self, name: impl Into<String>) -> crate::window::Window<'_> {
156 crate::window::Window::new(self, name)
157 }
158
159 #[doc(alias = "ShowDemoWindow")]
162 pub fn show_demo_window(&self, opened: &mut bool) {
163 unsafe {
164 crate::sys::igShowDemoWindow(opened);
165 }
166 }
167
168 #[doc(alias = "ImageWithBg")]
172 pub fn image_with_bg(
173 &self,
174 texture: impl Into<TextureRef>,
175 size: [f32; 2],
176 bg_color: [f32; 4],
177 tint_color: [f32; 4],
178 ) {
179 crate::widget::image::Image::new(self, texture, size).build_with_bg(bg_color, tint_color)
180 }
181
182 #[doc(alias = "ShowAboutWindow")]
186 pub fn show_about_window(&self, opened: &mut bool) {
187 unsafe {
188 crate::sys::igShowAboutWindow(opened);
189 }
190 }
191
192 #[doc(alias = "ShowMetricsWindow")]
197 pub fn show_metrics_window(&self, opened: &mut bool) {
198 unsafe {
199 crate::sys::igShowMetricsWindow(opened);
200 }
201 }
202
203 #[doc(alias = "ShowStyleEditor")]
205 pub fn show_style_editor(&self, style: &mut crate::style::Style) {
206 unsafe {
207 crate::sys::igShowStyleEditor(style.raw_mut());
208 }
209 }
210
211 #[doc(alias = "ShowStyleEditor")]
213 pub fn show_default_style_editor(&self) {
214 unsafe {
215 crate::sys::igShowStyleEditor(std::ptr::null_mut());
216 }
217 }
218
219 #[doc(alias = "ShowUserGuide")]
221 pub fn show_user_guide(&self) {
222 unsafe {
223 crate::sys::igShowUserGuide();
224 }
225 }
226
227 #[doc(alias = "DragFloat")]
231 pub fn drag_float(&self, label: impl AsRef<str>, value: &mut f32) -> bool {
232 crate::widget::drag::Drag::new(label).build(self, value)
233 }
234
235 #[doc(alias = "DragFloat")]
237 pub fn drag_float_config<L: AsRef<str>>(&self, label: L) -> crate::widget::drag::Drag<f32, L> {
238 crate::widget::drag::Drag::new(label)
239 }
240
241 #[doc(alias = "DragInt")]
243 pub fn drag_int(&self, label: impl AsRef<str>, value: &mut i32) -> bool {
244 crate::widget::drag::Drag::new(label).build(self, value)
245 }
246
247 #[doc(alias = "DragInt")]
249 pub fn drag_int_config<L: AsRef<str>>(&self, label: L) -> crate::widget::drag::Drag<i32, L> {
250 crate::widget::drag::Drag::new(label)
251 }
252
253 #[doc(alias = "DragFloatRange2")]
255 pub fn drag_float_range2(&self, label: impl AsRef<str>, min: &mut f32, max: &mut f32) -> bool {
256 crate::widget::drag::DragRange::<f32, _>::new(label).build(self, min, max)
257 }
258
259 #[doc(alias = "DragFloatRange2")]
261 pub fn drag_float_range2_config<L: AsRef<str>>(
262 &self,
263 label: L,
264 ) -> crate::widget::drag::DragRange<f32, L> {
265 crate::widget::drag::DragRange::new(label)
266 }
267
268 #[doc(alias = "DragIntRange2")]
270 pub fn drag_int_range2(&self, label: impl AsRef<str>, min: &mut i32, max: &mut i32) -> bool {
271 crate::widget::drag::DragRange::<i32, _>::new(label).build(self, min, max)
272 }
273
274 #[doc(alias = "DragIntRange2")]
276 pub fn drag_int_range2_config<L: AsRef<str>>(
277 &self,
278 label: L,
279 ) -> crate::widget::drag::DragRange<i32, L> {
280 crate::widget::drag::DragRange::new(label)
281 }
282
283 #[doc(alias = "GetMouseCursor")]
287 pub fn mouse_cursor(&self) -> Option<MouseCursor> {
288 unsafe {
289 match sys::igGetMouseCursor() {
290 sys::ImGuiMouseCursor_Arrow => Some(MouseCursor::Arrow),
291 sys::ImGuiMouseCursor_TextInput => Some(MouseCursor::TextInput),
292 sys::ImGuiMouseCursor_ResizeAll => Some(MouseCursor::ResizeAll),
293 sys::ImGuiMouseCursor_ResizeNS => Some(MouseCursor::ResizeNS),
294 sys::ImGuiMouseCursor_ResizeEW => Some(MouseCursor::ResizeEW),
295 sys::ImGuiMouseCursor_ResizeNESW => Some(MouseCursor::ResizeNESW),
296 sys::ImGuiMouseCursor_ResizeNWSE => Some(MouseCursor::ResizeNWSE),
297 sys::ImGuiMouseCursor_Hand => Some(MouseCursor::Hand),
298 sys::ImGuiMouseCursor_NotAllowed => Some(MouseCursor::NotAllowed),
299 _ => None,
300 }
301 }
302 }
303
304 #[doc(alias = "SetMouseCursor")]
308 pub fn set_mouse_cursor(&self, cursor_type: Option<MouseCursor>) {
309 unsafe {
310 let val: sys::ImGuiMouseCursor = cursor_type
311 .map(|x| x as sys::ImGuiMouseCursor)
312 .unwrap_or(sys::ImGuiMouseCursor_None);
313 sys::igSetMouseCursor(val);
314 }
315 }
316
317 #[doc(alias = "SetKeyboardFocusHere")]
326 pub fn set_keyboard_focus_here(&self) {
327 self.set_keyboard_focus_here_with_offset(0);
328 }
329
330 #[doc(alias = "SetKeyboardFocusHere")]
334 pub fn set_keyboard_focus_here_with_offset(&self, offset: i32) {
335 unsafe {
336 sys::igSetKeyboardFocusHere(offset);
337 }
338 }
339
340 #[doc(alias = "SetNextItemOpen")]
344 pub fn set_next_item_open(&self, is_open: bool) {
345 unsafe {
346 sys::igSetNextItemOpen(is_open, 0); }
348 }
349
350 #[doc(alias = "SetNextItemOpen")]
352 pub fn set_next_item_open_with_cond(&self, is_open: bool, cond: crate::Condition) {
353 unsafe { sys::igSetNextItemOpen(is_open, cond as sys::ImGuiCond) }
354 }
355
356 #[doc(alias = "SetNextItemWidth")]
360 pub fn set_next_item_width(&self, item_width: f32) {
361 unsafe {
362 sys::igSetNextItemWidth(item_width);
363 }
364 }
365
366 #[doc(alias = "GetStyle")]
382 pub unsafe fn style(&self) -> &crate::Style {
383 unsafe {
384 &*(sys::igGetStyle() as *const crate::Style)
386 }
387 }
388
389 #[doc(alias = "GetStyle")]
393 pub fn clone_style(&self) -> crate::Style {
394 unsafe { self.style().clone() }
395 }
396
397 #[doc(alias = "StyleColorsDark")]
399 pub fn style_colors_dark(&self) {
400 unsafe { sys::igStyleColorsDark(std::ptr::null_mut()) }
401 }
402
403 #[doc(alias = "StyleColorsLight")]
405 pub fn style_colors_light(&self) {
406 unsafe { sys::igStyleColorsLight(std::ptr::null_mut()) }
407 }
408
409 #[doc(alias = "StyleColorsClassic")]
411 pub fn style_colors_classic(&self) {
412 unsafe { sys::igStyleColorsClassic(std::ptr::null_mut()) }
413 }
414
415 #[doc(alias = "StyleColorsDark")]
417 pub fn style_colors_dark_into(&self, dst: &mut crate::Style) {
418 unsafe { sys::igStyleColorsDark(dst as *mut _ as *mut sys::ImGuiStyle) }
419 }
420
421 #[doc(alias = "StyleColorsLight")]
423 pub fn style_colors_light_into(&self, dst: &mut crate::Style) {
424 unsafe { sys::igStyleColorsLight(dst as *mut _ as *mut sys::ImGuiStyle) }
425 }
426
427 #[doc(alias = "StyleColorsClassic")]
429 pub fn style_colors_classic_into(&self, dst: &mut crate::Style) {
430 unsafe { sys::igStyleColorsClassic(dst as *mut _ as *mut sys::ImGuiStyle) }
431 }
432
433 #[doc(alias = "GetWindowDpiScale")]
435 pub fn window_dpi_scale(&self) -> f32 {
436 unsafe { sys::igGetWindowDpiScale() }
437 }
438
439 #[doc(alias = "Value")]
441 pub fn value_bool(&self, prefix: impl AsRef<str>, v: bool) {
442 unsafe { sys::igValue_Bool(self.scratch_txt(prefix), v) }
443 }
444
445 #[doc(alias = "GetWindowWidth")]
447 pub fn window_width(&self) -> f32 {
448 unsafe { sys::igGetWindowWidth() }
449 }
450
451 #[doc(alias = "GetWindowHeight")]
453 pub fn window_height(&self) -> f32 {
454 unsafe { sys::igGetWindowHeight() }
455 }
456
457 #[doc(alias = "GetWindowPos")]
459 pub fn window_pos(&self) -> [f32; 2] {
460 let v = unsafe { sys::igGetWindowPos() };
461 [v.x, v.y]
462 }
463
464 #[doc(alias = "GetWindowSize")]
466 pub fn window_size(&self) -> [f32; 2] {
467 let v = unsafe { sys::igGetWindowSize() };
468 [v.x, v.y]
469 }
470
471 #[doc(alias = "ShowDebugLogWindow")]
479 pub fn show_debug_log_window(&self, opened: &mut bool) {
480 unsafe {
481 sys::igShowDebugLogWindow(opened);
482 }
483 }
484
485 #[doc(alias = "ShowIDStackToolWindow")]
489 pub fn show_id_stack_tool_window(&self, opened: &mut bool) {
490 unsafe {
491 sys::igShowIDStackToolWindow(opened);
492 }
493 }
494
495 #[doc(alias = "ShowStyleSelector")]
499 pub fn show_style_selector(&self, label: impl AsRef<str>) -> bool {
500 unsafe { sys::igShowStyleSelector(self.scratch_txt(label)) }
501 }
502
503 #[doc(alias = "ShowFontSelector")]
505 pub fn show_font_selector(&self, label: impl AsRef<str>) {
506 unsafe {
507 sys::igShowFontSelector(self.scratch_txt(label));
508 }
509 }
510
511 #[doc(alias = "GetVersion")]
513 pub fn get_version(&self) -> &str {
514 unsafe {
515 let version_ptr = sys::igGetVersion();
516 let c_str = std::ffi::CStr::from_ptr(version_ptr);
517 c_str.to_str().unwrap_or("Unknown")
518 }
519 }
520}