mirror of
https://github.com/eliasstepanik/imgui-rs.git
synced 2026-01-11 13:38:35 +00:00
* add input_scalar
* allow setting display format for input_float
This commit is contained in:
parent
36aed0e4e1
commit
bb66413a29
@ -33,6 +33,8 @@ struct State {
|
||||
text_with_hint: String,
|
||||
text_multiline: String,
|
||||
i0: i32,
|
||||
u0: u64,
|
||||
d0: f64,
|
||||
f0: f32,
|
||||
vec2f: [f32; 2],
|
||||
vec3f: [f32; 3],
|
||||
@ -95,7 +97,9 @@ impl Default for State {
|
||||
text_with_hint,
|
||||
text_multiline,
|
||||
i0: 123,
|
||||
u0: 1234,
|
||||
f0: 0.001,
|
||||
d0: 0.0001,
|
||||
vec2f: [0.10, 0.20],
|
||||
vec3f: [0.10, 0.20, 0.30],
|
||||
vec2i: [10, 20],
|
||||
@ -538,15 +542,20 @@ fn show_test_window(ui: &Ui, state: &mut State, opened: &mut bool) {
|
||||
ui.input_int("input int", &mut state.i0).build();
|
||||
// Drag::new("drag int").build(ui, &mut state.i0);
|
||||
ui.input_float("input float", &mut state.f0)
|
||||
.step(0.01)
|
||||
.step_fast(1.0)
|
||||
.build();
|
||||
.step(0.01)
|
||||
.step_fast(1.0)
|
||||
.build();
|
||||
Drag::new("drag float").range(-1.0, 1.0).speed(0.001).build(ui, &mut state.f0);
|
||||
ui.input_float3("input float3", &mut state.vec3f)
|
||||
.build();
|
||||
.build();
|
||||
ColorEdit3::new("color 1", &mut state.col1).build(ui);
|
||||
ColorEdit4::new("color 2", &mut state.col2).build(ui);
|
||||
|
||||
ui.input_scalar("input scalar i64", &mut state.u0).build(ui);
|
||||
ui.input_scalar("input scalar f64", &mut state.d0).build(ui);
|
||||
ui.input_scalar_n("input scalar int array", &mut state.vec3i).build(ui);
|
||||
ui.input_scalar_n("input scalar float array", &mut state.vec3f).build(ui);
|
||||
|
||||
TreeNode::new("Multi-component Widgets").build(ui, || {
|
||||
ui.input_float2("input float2", &mut state.vec2f)
|
||||
.build();
|
||||
|
||||
@ -1,7 +1,9 @@
|
||||
use bitflags::bitflags;
|
||||
use std::ops::Range;
|
||||
use std::os::raw::{c_char, c_int, c_void};
|
||||
use std::ptr;
|
||||
|
||||
use crate::internal::DataTypeKind;
|
||||
use crate::math::*;
|
||||
use crate::sys;
|
||||
use crate::Ui;
|
||||
@ -514,11 +516,12 @@ impl<'ui, 'p, L: AsRef<str>> InputInt<'ui, 'p, L> {
|
||||
}
|
||||
|
||||
#[must_use]
|
||||
pub struct InputFloat<'ui, 'p, L> {
|
||||
pub struct InputFloat<'ui, 'p, L, F = &'static str> {
|
||||
label: L,
|
||||
value: &'p mut f32,
|
||||
step: f32,
|
||||
step_fast: f32,
|
||||
display_format: Option<F>,
|
||||
flags: InputTextFlags,
|
||||
ui: &'ui Ui,
|
||||
}
|
||||
@ -530,19 +533,36 @@ impl<'ui, 'p, L: AsRef<str>> InputFloat<'ui, 'p, L> {
|
||||
value,
|
||||
step: 0.0,
|
||||
step_fast: 0.0,
|
||||
display_format: None,
|
||||
flags: InputTextFlags::empty(),
|
||||
ui,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn display_format<F2: AsRef<str>>(self, display_format: F2) -> InputFloat<'ui, 'p, L, F2> {
|
||||
InputFloat {
|
||||
value: self.value,
|
||||
label: self.label,
|
||||
step: self.step,
|
||||
step_fast: self.step_fast,
|
||||
display_format: Some(display_format),
|
||||
flags: self.flags,
|
||||
ui: self.ui,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn build(self) -> bool {
|
||||
let (one, two) = self
|
||||
.ui
|
||||
.scratch_txt_with_opt(self.label, self.display_format);
|
||||
|
||||
unsafe {
|
||||
sys::igInputFloat(
|
||||
self.ui.scratch_txt(self.label),
|
||||
one,
|
||||
self.value as *mut f32,
|
||||
self.step,
|
||||
self.step_fast,
|
||||
b"%.3f\0".as_ptr() as *const _,
|
||||
two,
|
||||
self.flags.bits() as i32,
|
||||
)
|
||||
}
|
||||
@ -555,9 +575,10 @@ impl<'ui, 'p, L: AsRef<str>> InputFloat<'ui, 'p, L> {
|
||||
macro_rules! impl_input_floatn {
|
||||
($InputFloatN:ident, $MINT_TARGET:ty, $N:expr, $igInputFloatN:ident) => {
|
||||
#[must_use]
|
||||
pub struct $InputFloatN<'ui, 'p, L, T> {
|
||||
pub struct $InputFloatN<'ui, 'p, L, T, F = &'static str> {
|
||||
label: L,
|
||||
value: &'p mut T,
|
||||
display_format: Option<F>,
|
||||
flags: InputTextFlags,
|
||||
ui: &'ui Ui,
|
||||
}
|
||||
@ -572,22 +593,35 @@ macro_rules! impl_input_floatn {
|
||||
$InputFloatN {
|
||||
label,
|
||||
value,
|
||||
display_format: None,
|
||||
flags: InputTextFlags::empty(),
|
||||
ui,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn display_format<F2: AsRef<str>>(
|
||||
self,
|
||||
display_format: F2,
|
||||
) -> $InputFloatN<'ui, 'p, L, T, F2> {
|
||||
$InputFloatN {
|
||||
label: self.label,
|
||||
value: self.value,
|
||||
display_format: Some(display_format),
|
||||
flags: self.flags,
|
||||
ui: self.ui,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn build(self) -> bool {
|
||||
let value: $MINT_TARGET = (*self.value).into();
|
||||
let mut value: [f32; $N] = value.into();
|
||||
|
||||
let (one, two) = self
|
||||
.ui
|
||||
.scratch_txt_with_opt(self.label, self.display_format);
|
||||
|
||||
let changed = unsafe {
|
||||
sys::$igInputFloatN(
|
||||
self.ui.scratch_txt(self.label),
|
||||
value.as_mut_ptr(),
|
||||
b"%.3f\0".as_ptr() as *const _,
|
||||
self.flags.bits() as i32,
|
||||
)
|
||||
sys::$igInputFloatN(one, value.as_mut_ptr(), two, self.flags.bits() as i32)
|
||||
};
|
||||
|
||||
if changed {
|
||||
@ -661,6 +695,175 @@ impl_input_intn!(InputInt2, MintIVec2, 2, igInputInt2);
|
||||
impl_input_intn!(InputInt3, MintIVec3, 3, igInputInt3);
|
||||
impl_input_intn!(InputInt4, MintIVec4, 4, igInputInt4);
|
||||
|
||||
/// Builder for an input scalar widget.
|
||||
#[must_use]
|
||||
pub struct InputScalar<'ui, 'p, T, L, F = &'static str> {
|
||||
value: &'p mut T,
|
||||
label: L,
|
||||
step: Option<T>,
|
||||
step_fast: Option<T>,
|
||||
display_format: Option<F>,
|
||||
flags: InputTextFlags,
|
||||
ui: &'ui Ui,
|
||||
}
|
||||
|
||||
impl<'ui, 'p, L: AsRef<str>, T: DataTypeKind> InputScalar<'ui, 'p, T, L> {
|
||||
/// Constructs a new input scalar builder.
|
||||
#[doc(alias = "InputScalar", alias = "InputScalarN")]
|
||||
pub fn new(ui: &'ui Ui, label: L, value: &'p mut T) -> Self {
|
||||
InputScalar {
|
||||
value,
|
||||
label,
|
||||
step: None,
|
||||
step_fast: None,
|
||||
display_format: None,
|
||||
flags: InputTextFlags::empty(),
|
||||
ui,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<'ui, 'p, L: AsRef<str>, T: DataTypeKind, F: AsRef<str>> InputScalar<'ui, 'p, T, L, F> {
|
||||
/// Sets the display format using *a C-style printf string*
|
||||
pub fn display_format<F2: AsRef<str>>(
|
||||
self,
|
||||
display_format: F2,
|
||||
) -> InputScalar<'ui, 'p, T, L, F2> {
|
||||
InputScalar {
|
||||
value: self.value,
|
||||
label: self.label,
|
||||
step: self.step,
|
||||
step_fast: self.step_fast,
|
||||
display_format: Some(display_format),
|
||||
flags: self.flags,
|
||||
ui: self.ui,
|
||||
}
|
||||
}
|
||||
/// Builds an input scalar that is bound to the given value.
|
||||
///
|
||||
/// Returns true if the value was changed.
|
||||
pub fn build(self, ui: &Ui) -> bool {
|
||||
unsafe {
|
||||
let (one, two) = ui.scratch_txt_with_opt(self.label, self.display_format);
|
||||
|
||||
sys::igInputScalar(
|
||||
one,
|
||||
T::KIND as i32,
|
||||
self.value as *mut T as *mut c_void,
|
||||
self.step
|
||||
.as_ref()
|
||||
.map(|step| step as *const T)
|
||||
.unwrap_or(ptr::null()) as *const c_void,
|
||||
self.step_fast
|
||||
.as_ref()
|
||||
.map(|step| step as *const T)
|
||||
.unwrap_or(ptr::null()) as *const c_void,
|
||||
two,
|
||||
self.flags.bits() as i32,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn step(mut self, value: T) -> Self {
|
||||
self.step = Some(value);
|
||||
self
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn step_fast(mut self, value: T) -> Self {
|
||||
self.step_fast = Some(value);
|
||||
self
|
||||
}
|
||||
|
||||
impl_text_flags!(InputScalar);
|
||||
}
|
||||
|
||||
/// Builder for an input scalar widget.
|
||||
#[must_use]
|
||||
pub struct InputScalarN<'ui, 'p, T, L, F = &'static str> {
|
||||
values: &'p mut [T],
|
||||
label: L,
|
||||
step: Option<T>,
|
||||
step_fast: Option<T>,
|
||||
display_format: Option<F>,
|
||||
flags: InputTextFlags,
|
||||
ui: &'ui Ui,
|
||||
}
|
||||
|
||||
impl<'ui, 'p, L: AsRef<str>, T: DataTypeKind> InputScalarN<'ui, 'p, T, L> {
|
||||
/// Constructs a new input scalar builder.
|
||||
#[doc(alias = "InputScalarN")]
|
||||
pub fn new(ui: &'ui Ui, label: L, values: &'p mut [T]) -> Self {
|
||||
InputScalarN {
|
||||
values,
|
||||
label,
|
||||
step: None,
|
||||
step_fast: None,
|
||||
display_format: None,
|
||||
flags: InputTextFlags::empty(),
|
||||
ui,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<'ui, 'p, L: AsRef<str>, T: DataTypeKind, F: AsRef<str>> InputScalarN<'ui, 'p, T, L, F> {
|
||||
/// Sets the display format using *a C-style printf string*
|
||||
pub fn display_format<F2: AsRef<str>>(
|
||||
self,
|
||||
display_format: F2,
|
||||
) -> InputScalarN<'ui, 'p, T, L, F2> {
|
||||
InputScalarN {
|
||||
values: self.values,
|
||||
label: self.label,
|
||||
step: self.step,
|
||||
step_fast: self.step_fast,
|
||||
display_format: Some(display_format),
|
||||
flags: self.flags,
|
||||
ui: self.ui,
|
||||
}
|
||||
}
|
||||
/// Builds a horizontal array of multiple input scalars attached to the given slice.
|
||||
///
|
||||
/// Returns true if any value was changed.
|
||||
pub fn build(self, ui: &Ui) -> bool {
|
||||
unsafe {
|
||||
let (one, two) = ui.scratch_txt_with_opt(self.label, self.display_format);
|
||||
|
||||
sys::igInputScalarN(
|
||||
one,
|
||||
T::KIND as i32,
|
||||
self.values.as_mut_ptr() as *mut c_void,
|
||||
self.values.len() as i32,
|
||||
self.step
|
||||
.as_ref()
|
||||
.map(|step| step as *const T)
|
||||
.unwrap_or(ptr::null()) as *const c_void,
|
||||
self.step_fast
|
||||
.as_ref()
|
||||
.map(|step| step as *const T)
|
||||
.unwrap_or(ptr::null()) as *const c_void,
|
||||
two,
|
||||
self.flags.bits() as i32,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn step(mut self, value: T) -> Self {
|
||||
self.step = Some(value);
|
||||
self
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn step_fast(mut self, value: T) -> Self {
|
||||
self.step_fast = Some(value);
|
||||
self
|
||||
}
|
||||
|
||||
impl_text_flags!(InputScalar);
|
||||
}
|
||||
|
||||
bitflags!(
|
||||
/// Callback flags for an `InputText` widget. These correspond to
|
||||
/// the general textflags.
|
||||
|
||||
@ -551,6 +551,30 @@ impl<'ui> Ui {
|
||||
{
|
||||
InputInt4::new(self, label, value)
|
||||
}
|
||||
#[doc(alias = "InputScalar")]
|
||||
pub fn input_scalar<'p, L, T>(
|
||||
&'ui self,
|
||||
label: L,
|
||||
value: &'p mut T,
|
||||
) -> InputScalar<'ui, 'p, T, L>
|
||||
where
|
||||
L: AsRef<str>,
|
||||
T: internal::DataTypeKind,
|
||||
{
|
||||
InputScalar::new(self, label, value)
|
||||
}
|
||||
#[doc(alias = "InputScalarN")]
|
||||
pub fn input_scalar_n<'p, L, T>(
|
||||
&'ui self,
|
||||
label: L,
|
||||
values: &'p mut [T],
|
||||
) -> InputScalarN<'ui, 'p, T, L>
|
||||
where
|
||||
L: AsRef<str>,
|
||||
T: internal::DataTypeKind,
|
||||
{
|
||||
InputScalarN::new(self, label, values)
|
||||
}
|
||||
}
|
||||
|
||||
create_token!(
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user