mirror of
https://github.com/eliasstepanik/imgui-rs.git
synced 2026-01-11 05:28:35 +00:00
Use mutable references instead of return values
It seems to be more ergonomical with the underlying library
This commit is contained in:
parent
9a37676580
commit
eef67ddecc
@ -33,7 +33,7 @@ frame.window()
|
||||
## Core design questions and current choices
|
||||
|
||||
* Closures VS begin/end pairs (current choice: closures)
|
||||
* Mutable references VS return values (current choice: return values)
|
||||
* Mutable references VS return values (current choice: mutable references)
|
||||
* Passing around Frame<'fr> VS passing around &'fr Frame (current choice: Frame<'fr>)
|
||||
* Splitting the API to smaller pieces VS all draw calls in Frame (current choice: all draw calls in Frame)
|
||||
* Builder pattern for optional arguments VS something else (current choice: builder)
|
||||
|
||||
@ -23,7 +23,7 @@ fn main() {
|
||||
}
|
||||
}
|
||||
|
||||
fn hello_world<'a>(frame: &Frame<'a>) -> bool {
|
||||
fn hello_world<'a>(frame: &Frame<'a>) {
|
||||
frame.window()
|
||||
.name(im_str!("Hello world"))
|
||||
.size((300.0, 100.0), ImGuiSetCond_FirstUseEver)
|
||||
|
||||
@ -39,9 +39,8 @@ impl Support {
|
||||
self.imgui.set_mouse_down(&[self.mouse_pressed.0, self.mouse_pressed.1, self.mouse_pressed.2, false, false]);
|
||||
}
|
||||
|
||||
pub fn render<'fr, 'a: 'fr , F: FnMut(&Frame<'fr>) -> bool>(
|
||||
pub fn render<'fr, 'a: 'fr , F: FnMut(&Frame<'fr>)>(
|
||||
&'a mut self, clear_color: (f32, f32, f32, f32), mut f: F) -> bool {
|
||||
let mut result;
|
||||
let now = SteadyTime::now();
|
||||
let delta = now - self.last_frame;
|
||||
let delta_f = delta.num_nanoseconds().unwrap() as f32 / 1_000_000_000.0;
|
||||
@ -55,7 +54,7 @@ impl Support {
|
||||
|
||||
let (width, height) = target.get_dimensions();
|
||||
let frame = self.imgui.frame(width, height, delta_f);
|
||||
result = f(&frame);
|
||||
f(&frame);
|
||||
self.renderer.render(&mut target, frame).unwrap();
|
||||
|
||||
target.finish().unwrap();
|
||||
@ -64,7 +63,7 @@ impl Support {
|
||||
match event {
|
||||
Event::Closed |
|
||||
Event::KeyboardInput(ElementState::Pressed, _, Some(VirtualKeyCode::Escape))
|
||||
=> result = false,
|
||||
=> return false,
|
||||
Event::MouseMoved(pos) => self.mouse_pos = pos,
|
||||
Event::MouseInput(state, MouseButton::Left) =>
|
||||
self.mouse_pressed.0 = state == ElementState::Pressed,
|
||||
@ -75,6 +74,6 @@ impl Support {
|
||||
_ => ()
|
||||
}
|
||||
}
|
||||
result
|
||||
true
|
||||
}
|
||||
}
|
||||
|
||||
@ -75,7 +75,7 @@ impl Default for FileMenuState {
|
||||
}
|
||||
|
||||
struct AutoResizeState {
|
||||
lines: usize
|
||||
lines: i32
|
||||
}
|
||||
|
||||
impl Default for AutoResizeState {
|
||||
@ -91,12 +91,13 @@ fn main() {
|
||||
.. Default::default()
|
||||
};
|
||||
let mut support = Support::init();
|
||||
let mut opened = true;
|
||||
|
||||
loop {
|
||||
let active = support.render(state.clear_color, |frame| {
|
||||
show_test_window(frame, &mut state)
|
||||
show_test_window(frame, &mut state, &mut opened);
|
||||
});
|
||||
if !active { break }
|
||||
if !active || !opened { break }
|
||||
}
|
||||
}
|
||||
|
||||
@ -119,25 +120,25 @@ fn show_user_guide<'a>(frame: &Frame<'a>) {
|
||||
Use +- to subtract."));
|
||||
}
|
||||
|
||||
fn show_test_window<'a>(frame: &Frame<'a>, state: &mut State) -> bool {
|
||||
fn show_test_window<'a>(frame: &Frame<'a>, state: &mut State, opened: &mut bool) {
|
||||
if state.show_app_metrics {
|
||||
state.show_app_metrics = frame.show_metrics_window();
|
||||
frame.show_metrics_window(&mut state.show_app_metrics);
|
||||
}
|
||||
if state.show_app_main_menu_bar { show_example_app_main_menu_bar(frame, state) }
|
||||
if state.show_app_auto_resize {
|
||||
state.show_app_auto_resize = show_example_app_auto_resize(frame, &mut state.auto_resize_state);
|
||||
show_example_app_auto_resize(frame, &mut state.auto_resize_state, &mut state.show_app_auto_resize);
|
||||
}
|
||||
if state.show_app_fixed_overlay {
|
||||
state.show_app_fixed_overlay = show_example_app_fixed_overlay(frame);
|
||||
show_example_app_fixed_overlay(frame, &mut state.show_app_fixed_overlay);
|
||||
}
|
||||
if state.show_app_manipulating_window_title {
|
||||
show_example_app_manipulating_window_title(frame);
|
||||
}
|
||||
if state.show_app_about {
|
||||
state.show_app_about = frame.window()
|
||||
frame.window()
|
||||
.name(im_str!("About ImGui"))
|
||||
.always_auto_resize(true)
|
||||
.closable(true)
|
||||
.opened(&mut state.show_app_about)
|
||||
.build(|| {
|
||||
frame.text(ImStr::from_str(&format!("ImGui {}", imgui::get_version())));
|
||||
frame.separator();
|
||||
@ -157,7 +158,7 @@ fn show_test_window<'a>(frame: &Frame<'a>, state: &mut State) -> bool {
|
||||
.menu_bar(!state.no_menu)
|
||||
.bg_alpha(state.bg_alpha)
|
||||
.size((550.0, 680.0), ImGuiSetCond_FirstUseEver)
|
||||
.closable(true)
|
||||
.opened(opened)
|
||||
.build(|| {
|
||||
frame.text(im_str!("ImGui says hello."));
|
||||
frame.menu_bar(|| {
|
||||
@ -165,39 +166,28 @@ fn show_test_window<'a>(frame: &Frame<'a>, state: &mut State) -> bool {
|
||||
show_example_menu_file(frame, &mut state.file_menu);
|
||||
});
|
||||
frame.menu(im_str!("Examples")).build(|| {
|
||||
if frame.menu_item(im_str!("Main menu bar")).build() {
|
||||
state.show_app_main_menu_bar = !state.show_app_main_menu_bar;
|
||||
}
|
||||
if frame.menu_item(im_str!("Console")).build() {
|
||||
state.show_app_console = !state.show_app_console;
|
||||
}
|
||||
if frame.menu_item(im_str!("Simple layout")).build() {
|
||||
state.show_app_layout = !state.show_app_layout;
|
||||
}
|
||||
if frame.menu_item(im_str!("Long text display")).build() {
|
||||
state.show_app_long_text = !state.show_app_long_text;
|
||||
}
|
||||
if frame.menu_item(im_str!("Auto-resizing window")).build() {
|
||||
state.show_app_auto_resize = !state.show_app_auto_resize;
|
||||
}
|
||||
if frame.menu_item(im_str!("Simple overlay")).build() {
|
||||
state.show_app_fixed_overlay = !state.show_app_fixed_overlay;
|
||||
}
|
||||
if frame.menu_item(im_str!("Manipulating window title")).build() {
|
||||
state.show_app_manipulating_window_title =
|
||||
!state.show_app_manipulating_window_title;
|
||||
}
|
||||
if frame.menu_item(im_str!("Custom rendering")).build() {
|
||||
state.show_app_custom_rendering = !state.show_app_custom_rendering;
|
||||
}
|
||||
frame.menu_item(im_str!("Main menu bar"))
|
||||
.selected(&mut state.show_app_main_menu_bar).build();
|
||||
frame.menu_item(im_str!("Console"))
|
||||
.selected(&mut state.show_app_console).build();
|
||||
frame.menu_item(im_str!("Simple layout"))
|
||||
.selected(&mut state.show_app_layout).build();
|
||||
frame.menu_item(im_str!("Long text display"))
|
||||
.selected(&mut state.show_app_long_text).build();
|
||||
frame.menu_item(im_str!("Auto-resizing window"))
|
||||
.selected(&mut state.show_app_auto_resize).build();
|
||||
frame.menu_item(im_str!("Simple overlay"))
|
||||
.selected(&mut state.show_app_fixed_overlay).build();
|
||||
frame.menu_item(im_str!("Manipulating window title"))
|
||||
.selected(&mut state.show_app_manipulating_window_title).build();
|
||||
frame.menu_item(im_str!("Custom rendering"))
|
||||
.selected(&mut state.show_app_custom_rendering).build();
|
||||
});
|
||||
frame.menu(im_str!("Help")).build(|| {
|
||||
if frame.menu_item(im_str!("Metrics")).build() {
|
||||
state.show_app_metrics = !state.show_app_metrics;
|
||||
}
|
||||
if frame.menu_item(im_str!("About ImGui")).build() {
|
||||
state.show_app_about = !state.show_app_about;
|
||||
}
|
||||
frame.menu_item(im_str!("Metrics"))
|
||||
.selected(&mut state.show_app_metrics).build();
|
||||
frame.menu_item(im_str!("About ImGui"))
|
||||
.selected(&mut state.show_app_about).build();
|
||||
});
|
||||
});
|
||||
frame.spacing();
|
||||
@ -207,35 +197,18 @@ fn show_test_window<'a>(frame: &Frame<'a>, state: &mut State) -> bool {
|
||||
}
|
||||
|
||||
if frame.collapsing_header(im_str!("Window options")).build() {
|
||||
if let Some(no_titlebar) = frame.checkbox(im_str!("no titlebar"), state.no_titlebar) {
|
||||
state.no_titlebar = no_titlebar;
|
||||
}
|
||||
frame.checkbox(im_str!("no titlebar"), &mut state.no_titlebar);
|
||||
frame.same_line(150.0);
|
||||
if let Some(no_border) = frame.checkbox(im_str!("no border"), state.no_border) {
|
||||
state.no_border = no_border;
|
||||
}
|
||||
frame.checkbox(im_str!("no border"), &mut state.no_border);
|
||||
frame.same_line(300.0);
|
||||
if let Some(no_resize) = frame.checkbox(im_str!("no resize"), state.no_resize) {
|
||||
state.no_resize = no_resize;
|
||||
}
|
||||
if let Some(no_move) = frame.checkbox(im_str!("no move"), state.no_move) {
|
||||
state.no_move = no_move;
|
||||
}
|
||||
frame.checkbox(im_str!("no resize"), &mut state.no_resize);
|
||||
frame.checkbox(im_str!("no move"), &mut state.no_move);
|
||||
frame.same_line(150.0);
|
||||
if let Some(no_scrollbar) = frame.checkbox(im_str!("no scrollbar"), state.no_scrollbar) {
|
||||
state.no_scrollbar = no_scrollbar;
|
||||
}
|
||||
frame.checkbox(im_str!("no scrollbar"), &mut state.no_scrollbar);
|
||||
frame.same_line(300.0);
|
||||
if let Some(no_collapse) = frame.checkbox(im_str!("no collapse"), state.no_collapse) {
|
||||
state.no_collapse = no_collapse;
|
||||
}
|
||||
if let Some(no_menu) = frame.checkbox(im_str!("no menu"), state.no_menu) {
|
||||
state.no_menu = no_menu;
|
||||
}
|
||||
if let Some(bg_alpha) = frame.slider_f32(im_str!("bg alpha"),
|
||||
state.bg_alpha, 0.0, 1.0).build() {
|
||||
state.bg_alpha = bg_alpha;
|
||||
}
|
||||
frame.checkbox(im_str!("no collapse"), &mut state.no_collapse);
|
||||
frame.checkbox(im_str!("no menu"), &mut state.no_menu);
|
||||
frame.slider_f32(im_str!("bg alpha"), &mut state.bg_alpha, 0.0, 1.0).build();
|
||||
}
|
||||
})
|
||||
}
|
||||
@ -246,21 +219,21 @@ fn show_example_app_main_menu_bar<'a>(frame: &Frame<'a>, state: &mut State) {
|
||||
show_example_menu_file(frame, &mut state.file_menu);
|
||||
});
|
||||
frame.menu(im_str!("Edit")).build(|| {
|
||||
if frame.menu_item(im_str!("Undo")).shortcut(im_str!("CTRL+Z")).build() { }
|
||||
if frame.menu_item(im_str!("Redo"))
|
||||
.shortcut(im_str!("CTRL+Y")).enabled(false).build() { }
|
||||
frame.menu_item(im_str!("Undo")).shortcut(im_str!("CTRL+Z")).build();
|
||||
frame.menu_item(im_str!("Redo"))
|
||||
.shortcut(im_str!("CTRL+Y")).enabled(false).build();
|
||||
frame.separator();
|
||||
if frame.menu_item(im_str!("Cut")).shortcut(im_str!("CTRL+X")).build() { }
|
||||
if frame.menu_item(im_str!("Copy")).shortcut(im_str!("CTRL+C")).build() { }
|
||||
if frame.menu_item(im_str!("Paste")).shortcut(im_str!("CTRL+V")).build() { }
|
||||
frame.menu_item(im_str!("Cut")).shortcut(im_str!("CTRL+X")).build();
|
||||
frame.menu_item(im_str!("Copy")).shortcut(im_str!("CTRL+C")).build();
|
||||
frame.menu_item(im_str!("Paste")).shortcut(im_str!("CTRL+V")).build();
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
fn show_example_menu_file<'a>(frame: &Frame<'a>, state: &mut FileMenuState) {
|
||||
frame.menu_item(im_str!("(dummy menu)")).enabled(false).build();
|
||||
if frame.menu_item(im_str!("New")).build() { }
|
||||
if frame.menu_item(im_str!("Open")).shortcut(im_str!("Ctrl+O")).build() { }
|
||||
frame.menu_item(im_str!("New")).build();
|
||||
frame.menu_item(im_str!("Open")).shortcut(im_str!("Ctrl+O")).build();
|
||||
frame.menu(im_str!("Open Recent")).build(|| {
|
||||
frame.menu_item(im_str!("fish_hat.c")).build();
|
||||
frame.menu_item(im_str!("fish_hat.inl")).build();
|
||||
@ -273,13 +246,11 @@ fn show_example_menu_file<'a>(frame: &Frame<'a>, state: &mut FileMenuState) {
|
||||
});
|
||||
});
|
||||
});
|
||||
if frame.menu_item(im_str!("Save")).shortcut(im_str!("Ctrl+S")).build() { }
|
||||
if frame.menu_item(im_str!("Save As..")).build() { }
|
||||
frame.menu_item(im_str!("Save")).shortcut(im_str!("Ctrl+S")).build();
|
||||
frame.menu_item(im_str!("Save As..")).build();
|
||||
frame.separator();
|
||||
frame.menu(im_str!("Options")).build(|| {
|
||||
if frame.menu_item(im_str!("Enabled")).selected(state.enabled).build() {
|
||||
state.enabled = !state.enabled;
|
||||
}
|
||||
frame.menu_item(im_str!("Enabled")).selected(&mut state.enabled).build();
|
||||
// TODO
|
||||
});
|
||||
frame.menu(im_str!("Colors")).build(|| {
|
||||
@ -288,33 +259,31 @@ fn show_example_menu_file<'a>(frame: &Frame<'a>, state: &mut FileMenuState) {
|
||||
frame.menu(im_str!("Disabled")).enabled(false).build(|| {
|
||||
unreachable!();
|
||||
});
|
||||
if frame.menu_item(im_str!("Checked")).selected(true).build() { }
|
||||
if frame.menu_item(im_str!("Quit")).shortcut(im_str!("Alt+F4")).build() { }
|
||||
let mut checked = true;
|
||||
frame.menu_item(im_str!("Checked")).selected(&mut checked).build();
|
||||
frame.menu_item(im_str!("Quit")).shortcut(im_str!("Alt+F4")).build();
|
||||
}
|
||||
|
||||
fn show_example_app_auto_resize<'a>(frame: &Frame<'a>, state: &mut AutoResizeState) -> bool {
|
||||
fn show_example_app_auto_resize<'a>(frame: &Frame<'a>, state: &mut AutoResizeState, opened: &mut bool) {
|
||||
frame.window()
|
||||
.name(im_str!("Example: Auto-resizing window"))
|
||||
.closable(true)
|
||||
.opened(opened)
|
||||
.always_auto_resize(true)
|
||||
.build(|| {
|
||||
frame.text(im_str!("Window will resize every-frame to the size of its content.
|
||||
Note that you probably don't want to query the window size to
|
||||
output your content because that would create a feedback loop."));
|
||||
if let Some(lines) = frame.slider_i32(im_str!("Number of lines"),
|
||||
state.lines as i32, 1, 20).build() {
|
||||
state.lines = lines as usize;
|
||||
}
|
||||
frame.slider_i32(im_str!("Number of lines"), &mut state.lines, 1, 20).build();
|
||||
for i in 0 .. state.lines {
|
||||
frame.text(im_str!("{:2$}This is line {}", "", i, i * 4));
|
||||
frame.text(im_str!("{:2$}This is line {}", "", i, i as usize * 4));
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
fn show_example_app_fixed_overlay<'a>(frame: &Frame<'a>) -> bool {
|
||||
fn show_example_app_fixed_overlay<'a>(frame: &Frame<'a>, opened: &mut bool) {
|
||||
frame.window()
|
||||
.name(im_str!("Example: Fixed Overlay"))
|
||||
.closable(true)
|
||||
.opened(opened)
|
||||
.bg_alpha(0.3)
|
||||
.title_bar(false)
|
||||
.resizable(false)
|
||||
|
||||
24
src/lib.rs
24
src/lib.rs
@ -208,19 +208,15 @@ impl<'fr> Frame<'fr> {
|
||||
Ok(())
|
||||
}
|
||||
pub fn show_user_guide(&self) { unsafe { ffi::igShowUserGuide() }; }
|
||||
pub fn show_test_window(&self) -> bool {
|
||||
let mut opened = true;
|
||||
pub fn show_test_window(&self, opened: &mut bool) {
|
||||
unsafe {
|
||||
ffi::igShowTestWindow(&mut opened);
|
||||
ffi::igShowTestWindow(opened);
|
||||
}
|
||||
opened
|
||||
}
|
||||
pub fn show_metrics_window(&self) -> bool {
|
||||
let mut opened = true;
|
||||
pub fn show_metrics_window(&self, opened: &mut bool) {
|
||||
unsafe {
|
||||
ffi::igShowMetricsWindow(&mut opened);
|
||||
ffi::igShowMetricsWindow(opened);
|
||||
}
|
||||
opened
|
||||
}
|
||||
}
|
||||
|
||||
@ -286,23 +282,19 @@ impl<'fr> Frame<'fr> {
|
||||
pub fn collapsing_header<'p>(&self, label: ImStr<'p>) -> CollapsingHeader<'fr, 'p> {
|
||||
CollapsingHeader::new(label)
|
||||
}
|
||||
pub fn checkbox<'p>(&self, label: ImStr<'p>, value: bool) -> Option<bool> {
|
||||
let mut result = value;
|
||||
let changed = unsafe {
|
||||
ffi::igCheckbox(label.as_ptr(), &mut result)
|
||||
};
|
||||
if changed { Some(result) } else { None }
|
||||
pub fn checkbox<'p>(&self, label: ImStr<'p>, value: &'p mut bool) -> bool {
|
||||
unsafe { ffi::igCheckbox(label.as_ptr(), value) }
|
||||
}
|
||||
}
|
||||
|
||||
// Widgets: Sliders
|
||||
impl<'fr> Frame<'fr> {
|
||||
pub fn slider_f32<'p>(&self, label: ImStr<'p>,
|
||||
value: f32, min: f32, max: f32) -> SliderFloat<'fr, 'p> {
|
||||
value: &'p mut f32, min: f32, max: f32) -> SliderFloat<'fr, 'p> {
|
||||
SliderFloat::new(label, value, min, max)
|
||||
}
|
||||
pub fn slider_i32<'p>(&self, label: ImStr<'p>,
|
||||
value: i32, min: i32, max: i32) -> SliderInt<'fr, 'p> {
|
||||
value: &'p mut i32, min: i32, max: i32) -> SliderInt<'fr, 'p> {
|
||||
SliderInt::new(label, value, min, max)
|
||||
}
|
||||
}
|
||||
|
||||
12
src/menus.rs
12
src/menus.rs
@ -37,7 +37,7 @@ impl<'fr, 'p> Menu<'fr, 'p> {
|
||||
pub struct MenuItem<'fr, 'p> {
|
||||
label: ImStr<'p>,
|
||||
shortcut: Option<ImStr<'p>>,
|
||||
selected: bool,
|
||||
selected: Option<&'p mut bool>,
|
||||
enabled: bool,
|
||||
_phantom: PhantomData<&'fr Frame<'fr>>
|
||||
}
|
||||
@ -47,7 +47,7 @@ impl<'fr, 'p> MenuItem<'fr, 'p> {
|
||||
MenuItem {
|
||||
label: label,
|
||||
shortcut: None,
|
||||
selected: false,
|
||||
selected: None,
|
||||
enabled: true,
|
||||
_phantom: PhantomData
|
||||
}
|
||||
@ -60,9 +60,9 @@ impl<'fr, 'p> MenuItem<'fr, 'p> {
|
||||
}
|
||||
}
|
||||
#[inline]
|
||||
pub fn selected(self, selected: bool) -> Self {
|
||||
pub fn selected(self, selected: &'p mut bool) -> Self {
|
||||
MenuItem {
|
||||
selected: selected,
|
||||
selected: Some(selected),
|
||||
.. self
|
||||
}
|
||||
}
|
||||
@ -76,10 +76,10 @@ impl<'fr, 'p> MenuItem<'fr, 'p> {
|
||||
pub fn build(self) -> bool {
|
||||
let label = self.label.as_ptr();
|
||||
let shortcut = self.shortcut.map(|x| x.as_ptr()).unwrap_or(ptr::null());
|
||||
let selected = self.selected;
|
||||
let selected = self.selected.map(|x| x as *mut bool).unwrap_or(ptr::null_mut());
|
||||
let enabled = self.enabled;
|
||||
unsafe {
|
||||
ffi::igMenuItem(label, shortcut, selected, enabled)
|
||||
ffi::igMenuItemPtr(label, shortcut, selected, enabled)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,4 +1,3 @@
|
||||
use libc::{c_float, c_int};
|
||||
use std::marker::PhantomData;
|
||||
|
||||
use super::ffi;
|
||||
@ -8,7 +7,7 @@ use super::{Frame, ImStr};
|
||||
|
||||
pub struct SliderInt<'fr, 'p> {
|
||||
label: ImStr<'p>,
|
||||
value: i32,
|
||||
value: &'p mut i32,
|
||||
min: i32,
|
||||
max: i32,
|
||||
display_format: ImStr<'p>,
|
||||
@ -16,7 +15,7 @@ pub struct SliderInt<'fr, 'p> {
|
||||
}
|
||||
|
||||
impl<'fr, 'p> SliderInt<'fr, 'p> {
|
||||
pub fn new(label: ImStr<'p>, value: i32, min: i32, max: i32) -> Self {
|
||||
pub fn new(label: ImStr<'p>, value: &'p mut i32, min: i32, max: i32) -> Self {
|
||||
SliderInt {
|
||||
label: label,
|
||||
value: value,
|
||||
@ -33,22 +32,18 @@ impl<'fr, 'p> SliderInt<'fr, 'p> {
|
||||
.. self
|
||||
}
|
||||
}
|
||||
pub fn build(self) -> Option<i32> {
|
||||
let mut value = self.value;
|
||||
let changed = unsafe {
|
||||
ffi::igSliderInt(self.label.as_ptr(),
|
||||
&mut value,
|
||||
self.min, self.max,
|
||||
pub fn build(self) -> bool {
|
||||
unsafe {
|
||||
ffi::igSliderInt(self.label.as_ptr(), self.value, self.min, self.max,
|
||||
self.display_format.as_ptr()
|
||||
)
|
||||
};
|
||||
if changed { Some(value) } else { None }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub struct SliderFloat<'fr, 'p> {
|
||||
label: ImStr<'p>,
|
||||
value: f32,
|
||||
value: &'p mut f32,
|
||||
min: f32,
|
||||
max: f32,
|
||||
display_format: ImStr<'p>,
|
||||
@ -57,7 +52,7 @@ pub struct SliderFloat<'fr, 'p> {
|
||||
}
|
||||
|
||||
impl<'fr, 'p> SliderFloat<'fr, 'p> {
|
||||
pub fn new(label: ImStr<'p>, value: f32, min: f32, max: f32) -> Self {
|
||||
pub fn new(label: ImStr<'p>, value: &'p mut f32, min: f32, max: f32) -> Self {
|
||||
SliderFloat {
|
||||
label: label,
|
||||
value: value,
|
||||
@ -82,17 +77,13 @@ impl<'fr, 'p> SliderFloat<'fr, 'p> {
|
||||
.. self
|
||||
}
|
||||
}
|
||||
pub fn build(self) -> Option<f32> {
|
||||
let mut value = self.value;
|
||||
let changed = unsafe {
|
||||
ffi::igSliderFloat(self.label.as_ptr(),
|
||||
&mut value,
|
||||
self.min, self.max,
|
||||
pub fn build(self) -> bool {
|
||||
unsafe {
|
||||
ffi::igSliderFloat(self.label.as_ptr(), self.value, self.min, self.max,
|
||||
self.display_format.as_ptr(),
|
||||
self.power
|
||||
)
|
||||
};
|
||||
if changed { Some(value) } else { None }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1,4 +1,3 @@
|
||||
use libc::c_float;
|
||||
use std::marker::PhantomData;
|
||||
use std::ptr;
|
||||
|
||||
@ -20,7 +19,7 @@ pub struct Window<'fr, 'p> {
|
||||
size: (f32, f32),
|
||||
size_cond: ImGuiSetCond,
|
||||
name: ImStr<'p>,
|
||||
closable: bool,
|
||||
opened: Option<&'p mut bool>,
|
||||
bg_alpha: f32,
|
||||
flags: ImGuiWindowFlags,
|
||||
_phantom: PhantomData<&'fr Frame<'fr>>
|
||||
@ -34,7 +33,7 @@ impl<'fr, 'p> Window<'fr, 'p> {
|
||||
size: (0.0, 0.0),
|
||||
size_cond: ImGuiSetCond::empty(),
|
||||
name: unsafe { ImStr::from_bytes(b"Debug\0") },
|
||||
closable: false,
|
||||
opened: None,
|
||||
bg_alpha: -1.0,
|
||||
flags: ImGuiWindowFlags::empty(),
|
||||
_phantom: PhantomData
|
||||
@ -64,9 +63,9 @@ impl<'fr, 'p> Window<'fr, 'p> {
|
||||
}
|
||||
}
|
||||
#[inline]
|
||||
pub fn closable(self, closable: bool) -> Self {
|
||||
pub fn opened(self, opened: &'p mut bool) -> Self {
|
||||
Window {
|
||||
closable: closable,
|
||||
opened: Some(opened),
|
||||
.. self
|
||||
}
|
||||
}
|
||||
@ -160,8 +159,7 @@ impl<'fr, 'p> Window<'fr, 'p> {
|
||||
.. self
|
||||
}
|
||||
}
|
||||
pub fn build<F: FnOnce()>(self, f: F) -> bool {
|
||||
let mut opened = true;
|
||||
pub fn build<F: FnOnce()>(self, f: F) {
|
||||
let render = unsafe {
|
||||
if !self.pos_cond.is_empty() {
|
||||
ffi::igSetNextWindowPos(ImVec2::new(self.pos.0, self.pos.1), self.pos_cond);
|
||||
@ -170,7 +168,7 @@ impl<'fr, 'p> Window<'fr, 'p> {
|
||||
ffi::igSetNextWindowSize(ImVec2::new(self.size.0, self.size.1), self.size_cond);
|
||||
}
|
||||
ffi::igBegin2(self.name.as_ptr(),
|
||||
if self.closable { &mut opened } else { ptr::null_mut() },
|
||||
self.opened.map(|x| x as *mut bool).unwrap_or(ptr::null_mut()),
|
||||
ImVec2::new(0.0, 0.0), self.bg_alpha, self.flags
|
||||
)
|
||||
};
|
||||
@ -178,6 +176,5 @@ impl<'fr, 'p> Window<'fr, 'p> {
|
||||
f();
|
||||
}
|
||||
unsafe { ffi::igEnd() };
|
||||
opened
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user