mirror of
https://github.com/emilk/egui.git
synced 2026-06-26 22:53:14 -04:00
eframe: Replace Frame::update with fn logic and fn ui (#7775)
* Part of https://github.com/emilk/egui/issues/5113 * Part of https://github.com/emilk/egui/issues/3524 ## What This deprecates `eframe::App::update` and replaces it with two new functions: ```rs pub trait App { /// Called just before `ui`, and in the future this will /// also be called for background apps when needed. fn logic(&mut self, ctx: &egui::Context, frame: &mut Frame) { } /// Show your user interface to the user. fn ui(&mut self, ui: &mut egui::Ui, frame: &mut Frame); … } ``` Similarly, `Context::run` is deprecated in favor of `Context::run_ui`. `Plugin`s are now handed a `Ui` instead of just a `Context` in `on_begin/end_frame`. ## TODO …either in this PR or a later one * [x] Deprecate `App::update` * [x] Deprecate `Context::run` * [x] Change plugins to get a `Ui` * [x] Update kittest * [x] Change viewports to get UI:s (`show_viewport_immediate` etc) - https://github.com/emilk/egui/pull/7779 ## Later PRs * [ ] Deprecate `Panel::show` * [ ] Deprecate `CentralPanel::show` * [ ] Deprecate `CentralPanel` ?
This commit is contained in:
@@ -135,6 +135,31 @@ impl CreationContext<'_> {
|
|||||||
|
|
||||||
/// Implement this trait to write apps that can be compiled for both web/wasm and desktop/native using [`eframe`](https://github.com/emilk/egui/tree/main/crates/eframe).
|
/// Implement this trait to write apps that can be compiled for both web/wasm and desktop/native using [`eframe`](https://github.com/emilk/egui/tree/main/crates/eframe).
|
||||||
pub trait App {
|
pub trait App {
|
||||||
|
/// Called once before each call to [`Self::ui`],
|
||||||
|
/// and additionally also called when the UI is hidden, but [`egui::Context::request_repaint`] was called.
|
||||||
|
///
|
||||||
|
/// You may NOT show any ui or do any painting during the call to [`Self::logic`].
|
||||||
|
///
|
||||||
|
/// The [`egui::Context`] can be cloned and saved if you like.
|
||||||
|
///
|
||||||
|
/// To force another call to [`Self::logic`], call [`egui::Context::request_repaint`] at any time (e.g. from another thread).
|
||||||
|
fn logic(&mut self, ctx: &egui::Context, frame: &mut Frame) {
|
||||||
|
_ = (ctx, frame);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Called each time the UI needs repainting, which may be many times per second.
|
||||||
|
///
|
||||||
|
/// The given [`egui::Ui`] has no margin or background color.
|
||||||
|
/// You can wrap your UI code in [`egui::CentralPanel`] or a [`egui::Frame::central_panel`] to remedy this.
|
||||||
|
///
|
||||||
|
/// The [`egui::Ui::ctx`] can be cloned and saved if you like.
|
||||||
|
/// To force a repaint, call [`egui::Context::request_repaint`] at any time (e.g. from another thread).
|
||||||
|
///
|
||||||
|
/// This is called for the root viewport ([`egui::ViewportId::ROOT`]).
|
||||||
|
/// Use [`egui::Context::show_viewport_deferred`] to spawn additional viewports (windows).
|
||||||
|
/// (A "viewport" in egui means an native OS window).
|
||||||
|
fn ui(&mut self, ui: &mut egui::Ui, frame: &mut Frame);
|
||||||
|
|
||||||
/// Called each time the UI needs repainting, which may be many times per second.
|
/// Called each time the UI needs repainting, which may be many times per second.
|
||||||
///
|
///
|
||||||
/// Put your widgets into a [`egui::Panel`], [`egui::CentralPanel`], [`egui::Window`] or [`egui::Area`].
|
/// Put your widgets into a [`egui::Panel`], [`egui::CentralPanel`], [`egui::Window`] or [`egui::Area`].
|
||||||
@@ -146,7 +171,10 @@ pub trait App {
|
|||||||
/// This is called for the root viewport ([`egui::ViewportId::ROOT`]).
|
/// This is called for the root viewport ([`egui::ViewportId::ROOT`]).
|
||||||
/// Use [`egui::Context::show_viewport_deferred`] to spawn additional viewports (windows).
|
/// Use [`egui::Context::show_viewport_deferred`] to spawn additional viewports (windows).
|
||||||
/// (A "viewport" in egui means an native OS window).
|
/// (A "viewport" in egui means an native OS window).
|
||||||
fn update(&mut self, ctx: &egui::Context, frame: &mut Frame);
|
#[deprecated = "Use Self::ui instead"]
|
||||||
|
fn update(&mut self, ctx: &egui::Context, frame: &mut Frame) {
|
||||||
|
_ = (ctx, frame);
|
||||||
|
}
|
||||||
|
|
||||||
/// Get a handle to the app.
|
/// Get a handle to the app.
|
||||||
///
|
///
|
||||||
|
|||||||
@@ -35,7 +35,7 @@
|
|||||||
//!
|
//!
|
||||||
//! impl MyEguiApp {
|
//! impl MyEguiApp {
|
||||||
//! fn new(cc: &eframe::CreationContext<'_>) -> Self {
|
//! fn new(cc: &eframe::CreationContext<'_>) -> Self {
|
||||||
//! // Customize egui here with cc.egui_ctx.set_fonts and cc.egui_ctx.set_visuals.
|
//! // Customize egui here with cc.egui_ctx.set_fonts and cc.egui_ctx.set_global_style.
|
||||||
//! // Restore app state using cc.storage (requires the "persistence" feature).
|
//! // Restore app state using cc.storage (requires the "persistence" feature).
|
||||||
//! // Use the cc.gl (a glow::Context) to create graphics shaders and buffers that you can use
|
//! // Use the cc.gl (a glow::Context) to create graphics shaders and buffers that you can use
|
||||||
//! // for e.g. egui::PaintCallback.
|
//! // for e.g. egui::PaintCallback.
|
||||||
@@ -44,8 +44,8 @@
|
|||||||
//! }
|
//! }
|
||||||
//!
|
//!
|
||||||
//! impl eframe::App for MyEguiApp {
|
//! impl eframe::App for MyEguiApp {
|
||||||
//! fn update(&mut self, ctx: &egui::Context, frame: &mut eframe::Frame) {
|
//! fn ui(&mut self, ui: &mut egui::Ui, frame: &mut eframe::Frame) {
|
||||||
//! egui::CentralPanel::default().show(ctx, |ui| {
|
//! egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
//! ui.heading("Hello World!");
|
//! ui.heading("Hello World!");
|
||||||
//! });
|
//! });
|
||||||
//! }
|
//! }
|
||||||
@@ -232,7 +232,7 @@ pub mod icon_data;
|
|||||||
///
|
///
|
||||||
/// impl MyEguiApp {
|
/// impl MyEguiApp {
|
||||||
/// fn new(cc: &eframe::CreationContext<'_>) -> Self {
|
/// fn new(cc: &eframe::CreationContext<'_>) -> Self {
|
||||||
/// // Customize egui here with cc.egui_ctx.set_fonts and cc.egui_ctx.set_visuals.
|
/// // Customize egui here with cc.egui_ctx.set_fonts and cc.egui_ctx.set_global_style.
|
||||||
/// // Restore app state using cc.storage (requires the "persistence" feature).
|
/// // Restore app state using cc.storage (requires the "persistence" feature).
|
||||||
/// // Use the cc.gl (a glow::Context) to create graphics shaders and buffers that you can use
|
/// // Use the cc.gl (a glow::Context) to create graphics shaders and buffers that you can use
|
||||||
/// // for e.g. egui::PaintCallback.
|
/// // for e.g. egui::PaintCallback.
|
||||||
@@ -241,8 +241,8 @@ pub mod icon_data;
|
|||||||
/// }
|
/// }
|
||||||
///
|
///
|
||||||
/// impl eframe::App for MyEguiApp {
|
/// impl eframe::App for MyEguiApp {
|
||||||
/// fn update(&mut self, ctx: &egui::Context, frame: &mut eframe::Frame) {
|
/// fn ui(&mut self, ui: &mut egui::Ui, frame: &mut eframe::Frame) {
|
||||||
/// egui::CentralPanel::default().show(ctx, |ui| {
|
/// egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
/// ui.heading("Hello World!");
|
/// ui.heading("Hello World!");
|
||||||
/// });
|
/// });
|
||||||
/// }
|
/// }
|
||||||
@@ -312,8 +312,8 @@ pub fn run_native(
|
|||||||
/// }
|
/// }
|
||||||
///
|
///
|
||||||
/// impl eframe::App for MyEguiApp {
|
/// impl eframe::App for MyEguiApp {
|
||||||
/// fn update(&mut self, ctx: &egui::Context, frame: &mut eframe::Frame) {
|
/// fn ui(&mut self, ui: &mut egui::Ui, frame: &mut eframe::Frame) {
|
||||||
/// egui::CentralPanel::default().show(ctx, |ui| {
|
/// egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
/// ui.heading("Hello World!");
|
/// ui.heading("Hello World!");
|
||||||
/// });
|
/// });
|
||||||
/// }
|
/// }
|
||||||
@@ -399,8 +399,9 @@ fn init_native(app_name: &str, native_options: &mut NativeOptions) -> Renderer {
|
|||||||
/// let mut age = 42;
|
/// let mut age = 42;
|
||||||
///
|
///
|
||||||
/// let options = eframe::NativeOptions::default();
|
/// let options = eframe::NativeOptions::default();
|
||||||
/// eframe::run_simple_native("My egui App", options, move |ctx, _frame| {
|
/// eframe::run_ui_native("My egui App", options, move |ui, _frame| {
|
||||||
/// egui::CentralPanel::default().show(ctx, |ui| {
|
/// // Wrap everything in a CentralPanel so we get some margins and a background color:
|
||||||
|
/// egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
/// ui.heading("My egui Application");
|
/// ui.heading("My egui Application");
|
||||||
/// ui.horizontal(|ui| {
|
/// ui.horizontal(|ui| {
|
||||||
/// let name_label = ui.label("Your name: ");
|
/// let name_label = ui.label("Your name: ");
|
||||||
@@ -421,6 +422,65 @@ fn init_native(app_name: &str, native_options: &mut NativeOptions) -> Renderer {
|
|||||||
/// This function can fail if we fail to set up a graphics context.
|
/// This function can fail if we fail to set up a graphics context.
|
||||||
#[cfg(not(target_arch = "wasm32"))]
|
#[cfg(not(target_arch = "wasm32"))]
|
||||||
#[cfg(any(feature = "glow", feature = "wgpu_no_default_features"))]
|
#[cfg(any(feature = "glow", feature = "wgpu_no_default_features"))]
|
||||||
|
pub fn run_ui_native(
|
||||||
|
app_name: &str,
|
||||||
|
native_options: NativeOptions,
|
||||||
|
ui_fun: impl FnMut(&mut egui::Ui, &mut Frame) + 'static,
|
||||||
|
) -> Result {
|
||||||
|
struct SimpleApp<U> {
|
||||||
|
ui_fun: U,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<U: FnMut(&mut egui::Ui, &mut Frame) + 'static> App for SimpleApp<U> {
|
||||||
|
fn ui(&mut self, ui: &mut egui::Ui, frame: &mut Frame) {
|
||||||
|
(self.ui_fun)(ui, frame);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
run_native(
|
||||||
|
app_name,
|
||||||
|
native_options,
|
||||||
|
Box::new(|_cc| Ok(Box::new(SimpleApp { ui_fun }))),
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// The simplest way to get started when writing a native app.
|
||||||
|
///
|
||||||
|
/// This does NOT support persistence of custom user data. For that you need to use [`run_native`].
|
||||||
|
/// However, it DOES support persistence of egui data (window positions and sizes, how far the user has scrolled in a
|
||||||
|
/// [`ScrollArea`](egui::ScrollArea), etc.) if the persistence feature is enabled.
|
||||||
|
///
|
||||||
|
/// # Example
|
||||||
|
/// ``` no_run
|
||||||
|
/// fn main() -> eframe::Result {
|
||||||
|
/// // Our application state:
|
||||||
|
/// let mut name = "Arthur".to_owned();
|
||||||
|
/// let mut age = 42;
|
||||||
|
///
|
||||||
|
/// let options = eframe::NativeOptions::default();
|
||||||
|
/// eframe::run_simple_native("My egui App", options, move |ctx, _frame| {
|
||||||
|
/// egui::CentralPanel::default().show(ctx, |ui| {
|
||||||
|
/// ui.heading("My egui Application");
|
||||||
|
/// ui.horizontal(|ui| {
|
||||||
|
/// let name_label = ui.label("Your name: ");
|
||||||
|
/// ui.text_edit_singleline(&mut name)
|
||||||
|
/// .labelled_by(name_label.id);
|
||||||
|
/// });
|
||||||
|
/// ui.add(egui::Slider::new(&mut age, 0..=120).text("age"));
|
||||||
|
/// if ui.button("Increment").clicked() {
|
||||||
|
/// age += 1;
|
||||||
|
/// }
|
||||||
|
/// ui.label(format!("Hello '{name}', age {age}"));
|
||||||
|
/// });
|
||||||
|
/// })
|
||||||
|
/// }
|
||||||
|
/// ```
|
||||||
|
///
|
||||||
|
/// # Errors
|
||||||
|
/// This function can fail if we fail to set up a graphics context.
|
||||||
|
#[deprecated = "Use run_ui_native instead"]
|
||||||
|
#[cfg(not(target_arch = "wasm32"))]
|
||||||
|
#[cfg(any(feature = "glow", feature = "wgpu_no_default_features"))]
|
||||||
pub fn run_simple_native(
|
pub fn run_simple_native(
|
||||||
app_name: &str,
|
app_name: &str,
|
||||||
native_options: NativeOptions,
|
native_options: NativeOptions,
|
||||||
@@ -431,6 +491,8 @@ pub fn run_simple_native(
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl<U: FnMut(&egui::Context, &mut Frame) + 'static> App for SimpleApp<U> {
|
impl<U: FnMut(&egui::Context, &mut Frame) + 'static> App for SimpleApp<U> {
|
||||||
|
fn ui(&mut self, _ui: &mut egui::Ui, _frame: &mut Frame) {}
|
||||||
|
|
||||||
fn update(&mut self, ctx: &egui::Context, frame: &mut Frame) {
|
fn update(&mut self, ctx: &egui::Context, frame: &mut Frame) {
|
||||||
(self.update_fun)(ctx, frame);
|
(self.update_fun)(ctx, frame);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -272,14 +272,27 @@ impl EpiIntegration {
|
|||||||
|
|
||||||
app.raw_input_hook(&self.egui_ctx, &mut raw_input);
|
app.raw_input_hook(&self.egui_ctx, &mut raw_input);
|
||||||
|
|
||||||
let full_output = self.egui_ctx.run(raw_input, |egui_ctx| {
|
let full_output = self.egui_ctx.run_ui(raw_input, |ui| {
|
||||||
if let Some(viewport_ui_cb) = viewport_ui_cb {
|
if let Some(viewport_ui_cb) = viewport_ui_cb {
|
||||||
// Child viewport
|
// Child viewport
|
||||||
profiling::scope!("viewport_callback");
|
profiling::scope!("viewport_callback");
|
||||||
viewport_ui_cb(egui_ctx);
|
viewport_ui_cb(ui);
|
||||||
} else {
|
} else {
|
||||||
profiling::scope!("App::update");
|
{
|
||||||
app.update(egui_ctx, &mut self.frame);
|
profiling::scope!("App::logic");
|
||||||
|
app.logic(ui.ctx(), &mut self.frame);
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
profiling::scope!("App::update");
|
||||||
|
#[expect(deprecated)]
|
||||||
|
app.update(ui.ctx(), &mut self.frame);
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
profiling::scope!("App::ui");
|
||||||
|
app.ui(ui, &mut self.frame);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -1362,7 +1362,7 @@ fn initialize_or_update_viewport(
|
|||||||
ids: ViewportIdPair,
|
ids: ViewportIdPair,
|
||||||
class: ViewportClass,
|
class: ViewportClass,
|
||||||
mut builder: ViewportBuilder,
|
mut builder: ViewportBuilder,
|
||||||
viewport_ui_cb: Option<Arc<dyn Fn(&egui::Context) + Send + Sync>>,
|
viewport_ui_cb: Option<Arc<dyn Fn(&mut egui::Ui) + Send + Sync>>,
|
||||||
) -> &mut Viewport {
|
) -> &mut Viewport {
|
||||||
profiling::function_scope!();
|
profiling::function_scope!();
|
||||||
|
|
||||||
@@ -1494,8 +1494,8 @@ fn render_immediate_viewport(
|
|||||||
shapes,
|
shapes,
|
||||||
pixels_per_point,
|
pixels_per_point,
|
||||||
viewport_output,
|
viewport_output,
|
||||||
} = egui_ctx.run(input, |ctx| {
|
} = egui_ctx.run_ui(input, |ui| {
|
||||||
viewport_ui_cb(ctx);
|
viewport_ui_cb(ui);
|
||||||
});
|
});
|
||||||
|
|
||||||
// ---------------------------------------------------
|
// ---------------------------------------------------
|
||||||
|
|||||||
@@ -1027,8 +1027,8 @@ fn render_immediate_viewport(
|
|||||||
shapes,
|
shapes,
|
||||||
pixels_per_point,
|
pixels_per_point,
|
||||||
viewport_output,
|
viewport_output,
|
||||||
} = egui_ctx.run(input, |ctx| {
|
} = egui_ctx.run_ui(input, |ui| {
|
||||||
viewport_ui_cb(ctx);
|
viewport_ui_cb(ui);
|
||||||
});
|
});
|
||||||
|
|
||||||
// ------------------------------------------
|
// ------------------------------------------
|
||||||
@@ -1155,7 +1155,7 @@ fn initialize_or_update_viewport<'a>(
|
|||||||
ids: ViewportIdPair,
|
ids: ViewportIdPair,
|
||||||
class: ViewportClass,
|
class: ViewportClass,
|
||||||
mut builder: ViewportBuilder,
|
mut builder: ViewportBuilder,
|
||||||
viewport_ui_cb: Option<Arc<dyn Fn(&egui::Context) + Send + Sync>>,
|
viewport_ui_cb: Option<Arc<dyn Fn(&mut egui::Ui) + Send + Sync>>,
|
||||||
painter: &mut egui_wgpu::winit::Painter,
|
painter: &mut egui_wgpu::winit::Painter,
|
||||||
) -> &'a mut Viewport {
|
) -> &'a mut Viewport {
|
||||||
use std::collections::btree_map::Entry;
|
use std::collections::btree_map::Entry;
|
||||||
|
|||||||
@@ -273,8 +273,13 @@ impl AppRunner {
|
|||||||
|
|
||||||
self.app.raw_input_hook(&self.egui_ctx, &mut raw_input);
|
self.app.raw_input_hook(&self.egui_ctx, &mut raw_input);
|
||||||
|
|
||||||
let full_output = self.egui_ctx.run(raw_input, |egui_ctx| {
|
let full_output = self.egui_ctx.run_ui(raw_input, |ui| {
|
||||||
self.app.update(egui_ctx, &mut self.frame);
|
self.app.logic(ui.ctx(), &mut self.frame);
|
||||||
|
|
||||||
|
#[expect(deprecated)]
|
||||||
|
self.app.update(ui.ctx(), &mut self.frame);
|
||||||
|
|
||||||
|
self.app.ui(ui, &mut self.frame);
|
||||||
});
|
});
|
||||||
let egui::FullOutput {
|
let egui::FullOutput {
|
||||||
platform_output,
|
platform_output,
|
||||||
|
|||||||
@@ -291,13 +291,13 @@ impl<'a> PanelSizer<'a> {
|
|||||||
/// See the [module level docs](crate::containers::panel) for more details.
|
/// See the [module level docs](crate::containers::panel) for more details.
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
/// # egui::__run_test_ctx(|ctx| {
|
/// # egui::__run_test_ui(|ui| {
|
||||||
/// egui::Panel::left("my_left_panel").show(ctx, |ui| {
|
/// egui::Panel::left("my_left_panel").show_inside(ui, |ui| {
|
||||||
/// ui.label("Hello World!");
|
/// ui.label("Hello World!");
|
||||||
/// });
|
/// });
|
||||||
/// # });
|
/// # });
|
||||||
/// ```
|
/// ```
|
||||||
#[must_use = "You should call .show()"]
|
#[must_use = "You should call .show_inside()"]
|
||||||
pub struct Panel {
|
pub struct Panel {
|
||||||
side: PanelSide,
|
side: PanelSide,
|
||||||
id: Id,
|
id: Id,
|
||||||
@@ -963,16 +963,16 @@ impl Panel {
|
|||||||
/// See the [module level docs](crate::containers::panel) for more details.
|
/// See the [module level docs](crate::containers::panel) for more details.
|
||||||
///
|
///
|
||||||
/// ```
|
/// ```
|
||||||
/// # egui::__run_test_ctx(|ctx| {
|
/// # egui::__run_test_ui(|ui| {
|
||||||
/// egui::Panel::top("my_panel").show(ctx, |ui| {
|
/// egui::Panel::top("my_panel").show_inside(ui, |ui| {
|
||||||
/// ui.label("Hello World! From `Panel`, that must be before `CentralPanel`!");
|
/// ui.label("Hello World! From `Panel`, that must be before `CentralPanel`!");
|
||||||
/// });
|
/// });
|
||||||
/// egui::CentralPanel::default().show(ctx, |ui| {
|
/// egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
/// ui.label("Hello World!");
|
/// ui.label("Hello World!");
|
||||||
/// });
|
/// });
|
||||||
/// # });
|
/// # });
|
||||||
/// ```
|
/// ```
|
||||||
#[must_use = "You should call .show()"]
|
#[must_use = "You should call .show_inside()"]
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
pub struct CentralPanel {
|
pub struct CentralPanel {
|
||||||
frame: Option<Frame>,
|
frame: Option<Frame>,
|
||||||
|
|||||||
@@ -790,9 +790,13 @@ impl Context {
|
|||||||
|
|
||||||
#[must_use]
|
#[must_use]
|
||||||
fn run_ui_dyn(&self, new_input: RawInput, run_ui: &mut dyn FnMut(&mut Ui)) -> FullOutput {
|
fn run_ui_dyn(&self, new_input: RawInput, run_ui: &mut dyn FnMut(&mut Ui)) -> FullOutput {
|
||||||
|
let plugins = self.read(|ctx| ctx.plugins.ordered_plugins());
|
||||||
|
#[expect(deprecated)]
|
||||||
self.run(new_input, |ctx| {
|
self.run(new_input, |ctx| {
|
||||||
crate::CentralPanel::no_frame().show(ctx, |ui| {
|
crate::CentralPanel::no_frame().show(ctx, |ui| {
|
||||||
|
plugins.on_begin_pass(ui);
|
||||||
run_ui(ui);
|
run_ui(ui);
|
||||||
|
plugins.on_end_pass(ui);
|
||||||
});
|
});
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@@ -824,6 +828,7 @@ impl Context {
|
|||||||
/// ## See also
|
/// ## See also
|
||||||
/// * [`Self::run_ui`]
|
/// * [`Self::run_ui`]
|
||||||
#[must_use]
|
#[must_use]
|
||||||
|
#[deprecated = "Call run_ui instead"]
|
||||||
pub fn run(&self, new_input: RawInput, mut run_ui: impl FnMut(&Self)) -> FullOutput {
|
pub fn run(&self, new_input: RawInput, mut run_ui: impl FnMut(&Self)) -> FullOutput {
|
||||||
self.run_dyn(new_input, &mut run_ui)
|
self.run_dyn(new_input, &mut run_ui)
|
||||||
}
|
}
|
||||||
@@ -924,9 +929,6 @@ impl Context {
|
|||||||
plugins.on_input(&mut new_input);
|
plugins.on_input(&mut new_input);
|
||||||
|
|
||||||
self.write(|ctx| ctx.begin_pass(new_input));
|
self.write(|ctx| ctx.begin_pass(new_input));
|
||||||
|
|
||||||
// Plugins run just after the pass starts:
|
|
||||||
plugins.on_begin_pass(self);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// See [`Self::begin_pass`].
|
/// See [`Self::begin_pass`].
|
||||||
@@ -2378,15 +2380,14 @@ impl Context {
|
|||||||
crate::gui_zoom::zoom_with_keyboard(self);
|
crate::gui_zoom::zoom_with_keyboard(self);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Plugins run just before the pass ends.
|
|
||||||
let plugins = self.read(|ctx| ctx.plugins.ordered_plugins());
|
|
||||||
plugins.on_end_pass(self);
|
|
||||||
|
|
||||||
#[cfg(debug_assertions)]
|
#[cfg(debug_assertions)]
|
||||||
self.debug_painting();
|
self.debug_painting();
|
||||||
|
|
||||||
let mut output = self.write(|ctx| ctx.end_pass());
|
let mut output = self.write(|ctx| ctx.end_pass());
|
||||||
|
|
||||||
|
let plugins = self.read(|ctx| ctx.plugins.ordered_plugins());
|
||||||
plugins.on_output(&mut output);
|
plugins.on_output(&mut output);
|
||||||
|
|
||||||
output
|
output
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -4039,10 +4040,8 @@ impl Context {
|
|||||||
viewport.class = ViewportClass::Deferred;
|
viewport.class = ViewportClass::Deferred;
|
||||||
viewport.builder = viewport_builder;
|
viewport.builder = viewport_builder;
|
||||||
viewport.used = true;
|
viewport.used = true;
|
||||||
viewport.viewport_ui_cb = Some(Arc::new(move |ctx| {
|
viewport.viewport_ui_cb = Some(Arc::new(move |ui| {
|
||||||
crate::CentralPanel::no_frame().show(ctx, |ui| {
|
(viewport_ui_cb)(ui, ViewportClass::Deferred);
|
||||||
(viewport_ui_cb)(ui, ViewportClass::Deferred);
|
|
||||||
});
|
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -4118,10 +4117,8 @@ impl Context {
|
|||||||
let viewport = ImmediateViewport {
|
let viewport = ImmediateViewport {
|
||||||
ids,
|
ids,
|
||||||
builder,
|
builder,
|
||||||
viewport_ui_cb: Box::new(move |ctx| {
|
viewport_ui_cb: Box::new(move |ui| {
|
||||||
crate::CentralPanel::no_frame().show(ctx, |ui| {
|
*out = Some((viewport_ui_cb)(ui, ViewportClass::Immediate));
|
||||||
*out = Some((viewport_ui_cb)(ui, ViewportClass::Immediate));
|
|
||||||
});
|
|
||||||
}),
|
}),
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -4246,11 +4243,11 @@ mod test {
|
|||||||
// A single call, no request to discard:
|
// A single call, no request to discard:
|
||||||
{
|
{
|
||||||
let mut num_calls = 0;
|
let mut num_calls = 0;
|
||||||
let output = ctx.run(Default::default(), |ctx| {
|
let output = ctx.run_ui(Default::default(), |ui| {
|
||||||
num_calls += 1;
|
num_calls += 1;
|
||||||
assert_eq!(ctx.output(|o| o.num_completed_passes), 0);
|
assert_eq!(ui.output(|o| o.num_completed_passes), 0);
|
||||||
assert!(!ctx.output(|o| o.requested_discard()));
|
assert!(!ui.output(|o| o.requested_discard()));
|
||||||
assert!(!ctx.will_discard());
|
assert!(!ui.will_discard());
|
||||||
});
|
});
|
||||||
assert_eq!(num_calls, 1);
|
assert_eq!(num_calls, 1);
|
||||||
assert_eq!(output.platform_output.num_completed_passes, 1);
|
assert_eq!(output.platform_output.num_completed_passes, 1);
|
||||||
@@ -4260,10 +4257,10 @@ mod test {
|
|||||||
// A single call, with a denied request to discard:
|
// A single call, with a denied request to discard:
|
||||||
{
|
{
|
||||||
let mut num_calls = 0;
|
let mut num_calls = 0;
|
||||||
let output = ctx.run(Default::default(), |ctx| {
|
let output = ctx.run_ui(Default::default(), |ui| {
|
||||||
num_calls += 1;
|
num_calls += 1;
|
||||||
ctx.request_discard("test");
|
ui.request_discard("test");
|
||||||
assert!(!ctx.will_discard(), "The request should have been denied");
|
assert!(!ui.will_discard(), "The request should have been denied");
|
||||||
});
|
});
|
||||||
assert_eq!(num_calls, 1);
|
assert_eq!(num_calls, 1);
|
||||||
assert_eq!(output.platform_output.num_completed_passes, 1);
|
assert_eq!(output.platform_output.num_completed_passes, 1);
|
||||||
@@ -4291,10 +4288,10 @@ mod test {
|
|||||||
// Normal single pass:
|
// Normal single pass:
|
||||||
{
|
{
|
||||||
let mut num_calls = 0;
|
let mut num_calls = 0;
|
||||||
let output = ctx.run(Default::default(), |ctx| {
|
let output = ctx.run_ui(Default::default(), |ui| {
|
||||||
assert_eq!(ctx.output(|o| o.num_completed_passes), 0);
|
assert_eq!(ui.output(|o| o.num_completed_passes), 0);
|
||||||
assert!(!ctx.output(|o| o.requested_discard()));
|
assert!(!ui.output(|o| o.requested_discard()));
|
||||||
assert!(!ctx.will_discard());
|
assert!(!ui.will_discard());
|
||||||
num_calls += 1;
|
num_calls += 1;
|
||||||
});
|
});
|
||||||
assert_eq!(num_calls, 1);
|
assert_eq!(num_calls, 1);
|
||||||
@@ -4305,13 +4302,13 @@ mod test {
|
|||||||
// Request discard once:
|
// Request discard once:
|
||||||
{
|
{
|
||||||
let mut num_calls = 0;
|
let mut num_calls = 0;
|
||||||
let output = ctx.run(Default::default(), |ctx| {
|
let output = ctx.run_ui(Default::default(), |ui| {
|
||||||
assert_eq!(ctx.output(|o| o.num_completed_passes), num_calls);
|
assert_eq!(ui.output(|o| o.num_completed_passes), num_calls);
|
||||||
|
|
||||||
assert!(!ctx.will_discard());
|
assert!(!ui.will_discard());
|
||||||
if num_calls == 0 {
|
if num_calls == 0 {
|
||||||
ctx.request_discard("test");
|
ui.request_discard("test");
|
||||||
assert!(ctx.will_discard());
|
assert!(ui.will_discard());
|
||||||
}
|
}
|
||||||
|
|
||||||
num_calls += 1;
|
num_calls += 1;
|
||||||
@@ -4327,15 +4324,15 @@ mod test {
|
|||||||
// Request discard twice:
|
// Request discard twice:
|
||||||
{
|
{
|
||||||
let mut num_calls = 0;
|
let mut num_calls = 0;
|
||||||
let output = ctx.run(Default::default(), |ctx| {
|
let output = ctx.run_ui(Default::default(), |ui| {
|
||||||
assert_eq!(ctx.output(|o| o.num_completed_passes), num_calls);
|
assert_eq!(ui.output(|o| o.num_completed_passes), num_calls);
|
||||||
|
|
||||||
assert!(!ctx.will_discard());
|
assert!(!ui.will_discard());
|
||||||
ctx.request_discard("test");
|
ui.request_discard("test");
|
||||||
if num_calls == 0 {
|
if num_calls == 0 {
|
||||||
assert!(ctx.will_discard(), "First request granted");
|
assert!(ui.will_discard(), "First request granted");
|
||||||
} else {
|
} else {
|
||||||
assert!(!ctx.will_discard(), "Second request should be denied");
|
assert!(!ui.will_discard(), "Second request should be denied");
|
||||||
}
|
}
|
||||||
|
|
||||||
num_calls += 1;
|
num_calls += 1;
|
||||||
@@ -4357,13 +4354,13 @@ mod test {
|
|||||||
// Request discard three times:
|
// Request discard three times:
|
||||||
{
|
{
|
||||||
let mut num_calls = 0;
|
let mut num_calls = 0;
|
||||||
let output = ctx.run(Default::default(), |ctx| {
|
let output = ctx.run_ui(Default::default(), |ui| {
|
||||||
assert_eq!(ctx.output(|o| o.num_completed_passes), num_calls);
|
assert_eq!(ui.output(|o| o.num_completed_passes), num_calls);
|
||||||
|
|
||||||
assert!(!ctx.will_discard());
|
assert!(!ui.will_discard());
|
||||||
if num_calls <= 2 {
|
if num_calls <= 2 {
|
||||||
ctx.request_discard("test");
|
ui.request_discard("test");
|
||||||
assert!(ctx.will_discard());
|
assert!(ui.will_discard());
|
||||||
}
|
}
|
||||||
|
|
||||||
num_calls += 1;
|
num_calls += 1;
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
//! to get callbacks on certain events ([`Plugin::on_begin_pass`], [`Plugin::on_end_pass`]).
|
//! to get callbacks on certain events ([`Plugin::on_begin_pass`], [`Plugin::on_end_pass`]).
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
Align, Align2, Color32, Context, FontFamily, FontId, Plugin, Rect, Shape, Vec2, WidgetText,
|
Align, Align2, Color32, Context, FontFamily, FontId, Plugin, Rect, Shape, Ui, Vec2, WidgetText,
|
||||||
text,
|
text,
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -57,9 +57,9 @@ impl Plugin for DebugTextPlugin {
|
|||||||
"DebugTextPlugin"
|
"DebugTextPlugin"
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_end_pass(&mut self, ctx: &Context) {
|
fn on_end_pass(&mut self, ui: &mut Ui) {
|
||||||
let entries = std::mem::take(&mut self.entries);
|
let entries = std::mem::take(&mut self.entries);
|
||||||
Self::paint_entries(ctx, entries);
|
Self::paint_entries(ui, entries);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
use std::{any::Any, sync::Arc};
|
use std::{any::Any, sync::Arc};
|
||||||
|
|
||||||
use crate::{Context, CursorIcon, Plugin};
|
use crate::{Context, CursorIcon, Plugin, Ui};
|
||||||
|
|
||||||
/// Plugin for tracking drag-and-drop payload.
|
/// Plugin for tracking drag-and-drop payload.
|
||||||
///
|
///
|
||||||
@@ -32,12 +32,12 @@ impl Plugin for DragAndDrop {
|
|||||||
/// Interrupt drag-and-drop if the user presses the escape key.
|
/// Interrupt drag-and-drop if the user presses the escape key.
|
||||||
///
|
///
|
||||||
/// This needs to happen at frame start so we can properly capture the escape key.
|
/// This needs to happen at frame start so we can properly capture the escape key.
|
||||||
fn on_begin_pass(&mut self, ctx: &Context) {
|
fn on_begin_pass(&mut self, ui: &mut Ui) {
|
||||||
let has_any_payload = self.payload.is_some();
|
let has_any_payload = self.payload.is_some();
|
||||||
|
|
||||||
if has_any_payload {
|
if has_any_payload {
|
||||||
let abort_dnd_due_to_escape_key =
|
let abort_dnd_due_to_escape_key =
|
||||||
ctx.input_mut(|i| i.consume_key(crate::Modifiers::NONE, crate::Key::Escape));
|
ui.input_mut(|i| i.consume_key(crate::Modifiers::NONE, crate::Key::Escape));
|
||||||
|
|
||||||
if abort_dnd_due_to_escape_key {
|
if abort_dnd_due_to_escape_key {
|
||||||
self.payload = None;
|
self.payload = None;
|
||||||
@@ -50,18 +50,18 @@ impl Plugin for DragAndDrop {
|
|||||||
/// This is a catch-all safety net in case user code doesn't capture the drag payload itself.
|
/// This is a catch-all safety net in case user code doesn't capture the drag payload itself.
|
||||||
/// This must happen at end-of-frame such that we don't shadow the mouse release event from user
|
/// This must happen at end-of-frame such that we don't shadow the mouse release event from user
|
||||||
/// code.
|
/// code.
|
||||||
fn on_end_pass(&mut self, ctx: &Context) {
|
fn on_end_pass(&mut self, ui: &mut Ui) {
|
||||||
let has_any_payload = self.payload.is_some();
|
let has_any_payload = self.payload.is_some();
|
||||||
|
|
||||||
if has_any_payload {
|
if has_any_payload {
|
||||||
let abort_dnd_due_to_mouse_release = ctx.input_mut(|i| i.pointer.any_released());
|
let abort_dnd_due_to_mouse_release = ui.input_mut(|i| i.pointer.any_released());
|
||||||
|
|
||||||
if abort_dnd_due_to_mouse_release {
|
if abort_dnd_due_to_mouse_release {
|
||||||
self.payload = None;
|
self.payload = None;
|
||||||
} else {
|
} else {
|
||||||
// We set the cursor icon only if its default, as the user code might have
|
// We set the cursor icon only if its default, as the user code might have
|
||||||
// explicitly set it already.
|
// explicitly set it already.
|
||||||
ctx.output_mut(|o| {
|
ui.output_mut(|o| {
|
||||||
if o.cursor_icon == CursorIcon::Default {
|
if o.cursor_icon == CursorIcon::Default {
|
||||||
o.cursor_icon = CursorIcon::Grabbing;
|
o.cursor_icon = CursorIcon::Grabbing;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -43,23 +43,6 @@
|
|||||||
//! In some GUI frameworks this would require defining multiple types and functions with callbacks or message handlers,
|
//! In some GUI frameworks this would require defining multiple types and functions with callbacks or message handlers,
|
||||||
//! but thanks to `egui` being immediate mode everything is one self-contained function!
|
//! but thanks to `egui` being immediate mode everything is one self-contained function!
|
||||||
//!
|
//!
|
||||||
//! ### Getting a [`Ui`]
|
|
||||||
//!
|
|
||||||
//! Use one of [`Panel`], [`CentralPanel`], [`Window`] or [`Area`] to
|
|
||||||
//! get access to an [`Ui`] where you can put widgets. For example:
|
|
||||||
//!
|
|
||||||
//! ```
|
|
||||||
//! # egui::__run_test_ctx(|ctx| {
|
|
||||||
//! egui::CentralPanel::default().show(&ctx, |ui| {
|
|
||||||
//! ui.add(egui::Label::new("Hello World!"));
|
|
||||||
//! ui.label("A shorter and more convenient way to add a label.");
|
|
||||||
//! if ui.button("Click me").clicked() {
|
|
||||||
//! // take some action here
|
|
||||||
//! }
|
|
||||||
//! });
|
|
||||||
//! # });
|
|
||||||
//! ```
|
|
||||||
//!
|
|
||||||
//! ### Quick start
|
//! ### Quick start
|
||||||
//!
|
//!
|
||||||
//! ```
|
//! ```
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
use crate::{Context, FullOutput, RawInput};
|
use crate::{Context, FullOutput, RawInput, Ui};
|
||||||
use ahash::HashMap;
|
use ahash::HashMap;
|
||||||
use epaint::mutex::{Mutex, MutexGuard};
|
use epaint::mutex::{Mutex, MutexGuard};
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
@@ -23,13 +23,13 @@ pub trait Plugin: Send + Sync + std::any::Any + 'static {
|
|||||||
|
|
||||||
/// Called at the start of each pass.
|
/// Called at the start of each pass.
|
||||||
///
|
///
|
||||||
/// Can be used to show ui, e.g. a [`crate::Window`] or [`crate::SidePanel`].
|
/// Can be used to show ui, e.g. a [`crate::Window`] or [`crate::Panel`].
|
||||||
fn on_begin_pass(&mut self, ctx: &Context) {}
|
fn on_begin_pass(&mut self, ui: &mut Ui) {}
|
||||||
|
|
||||||
/// Called at the end of each pass.
|
/// Called at the end of each pass.
|
||||||
///
|
///
|
||||||
/// Can be used to show ui, e.g. a [`crate::Window`].
|
/// Can be used to show ui, e.g. a [`crate::Window`].
|
||||||
fn on_end_pass(&mut self, ctx: &Context) {}
|
fn on_end_pass(&mut self, ui: &mut Ui) {}
|
||||||
|
|
||||||
/// Called just before the input is processed.
|
/// Called just before the input is processed.
|
||||||
///
|
///
|
||||||
@@ -147,17 +147,17 @@ impl PluginsOrdered {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_begin_pass(&self, ctx: &Context) {
|
pub fn on_begin_pass(&self, ui: &mut Ui) {
|
||||||
profiling::scope!("plugins", "on_begin_pass");
|
profiling::scope!("plugins", "on_begin_pass");
|
||||||
self.for_each_dyn(|p| {
|
self.for_each_dyn(|p| {
|
||||||
p.on_begin_pass(ctx);
|
p.on_begin_pass(ui);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_end_pass(&self, ctx: &Context) {
|
pub fn on_end_pass(&self, ui: &mut Ui) {
|
||||||
profiling::scope!("plugins", "on_end_pass");
|
profiling::scope!("plugins", "on_end_pass");
|
||||||
self.for_each_dyn(|p| {
|
self.for_each_dyn(|p| {
|
||||||
p.on_end_pass(ctx);
|
p.on_end_pass(ui);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -214,7 +214,7 @@ impl Plugins {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Generic event callback.
|
/// Generic event callback.
|
||||||
pub type ContextCallback = Arc<dyn Fn(&Context) + Send + Sync>;
|
pub type ContextCallback = Arc<dyn Fn(&mut Ui) + Send + Sync>;
|
||||||
|
|
||||||
#[derive(Default)]
|
#[derive(Default)]
|
||||||
pub(crate) struct CallbackPlugin {
|
pub(crate) struct CallbackPlugin {
|
||||||
@@ -227,21 +227,21 @@ impl Plugin for CallbackPlugin {
|
|||||||
"CallbackPlugins"
|
"CallbackPlugins"
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_begin_pass(&mut self, ctx: &Context) {
|
fn on_begin_pass(&mut self, ui: &mut Ui) {
|
||||||
profiling::function_scope!();
|
profiling::function_scope!();
|
||||||
|
|
||||||
for (_debug_name, cb) in &self.on_begin_plugins {
|
for (_debug_name, cb) in &self.on_begin_plugins {
|
||||||
profiling::scope!("on_begin_pass", *_debug_name);
|
profiling::scope!("on_begin_pass", *_debug_name);
|
||||||
(cb)(ctx);
|
(cb)(ui);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_end_pass(&mut self, ctx: &Context) {
|
fn on_end_pass(&mut self, ui: &mut Ui) {
|
||||||
profiling::function_scope!();
|
profiling::function_scope!();
|
||||||
|
|
||||||
for (_debug_name, cb) in &self.on_end_plugins {
|
for (_debug_name, cb) in &self.on_end_plugins {
|
||||||
profiling::scope!("on_end_pass", *_debug_name);
|
profiling::scope!("on_end_pass", *_debug_name);
|
||||||
(cb)(ctx);
|
(cb)(ui);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -128,8 +128,8 @@ impl Plugin for LabelSelectionState {
|
|||||||
"LabelSelectionState"
|
"LabelSelectionState"
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_begin_pass(&mut self, ctx: &Context) {
|
fn on_begin_pass(&mut self, ui: &mut Ui) {
|
||||||
if ctx.input(|i| i.pointer.any_pressed() && !i.modifiers.shift) {
|
if ui.input(|i| i.pointer.any_pressed() && !i.modifiers.shift) {
|
||||||
// Maybe a new selection is about to begin, but the old one is over:
|
// Maybe a new selection is about to begin, but the old one is over:
|
||||||
// state.selection = None; // TODO(emilk): this makes sense, but doesn't work as expected.
|
// state.selection = None; // TODO(emilk): this makes sense, but doesn't work as expected.
|
||||||
}
|
}
|
||||||
@@ -145,9 +145,9 @@ impl Plugin for LabelSelectionState {
|
|||||||
self.painted_selections.clear();
|
self.painted_selections.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_end_pass(&mut self, ctx: &Context) {
|
fn on_end_pass(&mut self, ui: &mut Ui) {
|
||||||
if self.is_dragging {
|
if self.is_dragging {
|
||||||
ctx.set_cursor_icon(CursorIcon::Text);
|
ui.set_cursor_icon(CursorIcon::Text);
|
||||||
}
|
}
|
||||||
|
|
||||||
if !self.has_reached_primary || !self.has_reached_secondary {
|
if !self.has_reached_primary || !self.has_reached_secondary {
|
||||||
@@ -159,7 +159,7 @@ impl Plugin for LabelSelectionState {
|
|||||||
if let Some(selection) = prev_selection {
|
if let Some(selection) = prev_selection {
|
||||||
// This was the first frame of glitch, so hide the
|
// This was the first frame of glitch, so hide the
|
||||||
// glitching by removing all painted selections:
|
// glitching by removing all painted selections:
|
||||||
ctx.graphics_mut(|layers| {
|
ui.graphics_mut(|layers| {
|
||||||
if let Some(list) = layers.get_mut(selection.layer_id) {
|
if let Some(list) = layers.get_mut(selection.layer_id) {
|
||||||
for (shape_idx, row_selections) in self.painted_selections.drain(..) {
|
for (shape_idx, row_selections) in self.painted_selections.drain(..) {
|
||||||
list.mutate_shape(shape_idx, |shape| {
|
list.mutate_shape(shape_idx, |shape| {
|
||||||
@@ -190,21 +190,21 @@ impl Plugin for LabelSelectionState {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let pressed_escape = ctx.input(|i| i.key_pressed(crate::Key::Escape));
|
let pressed_escape = ui.input(|i| i.key_pressed(crate::Key::Escape));
|
||||||
let clicked_something_else = ctx.input(|i| i.pointer.any_pressed()) && !self.any_hovered;
|
let clicked_something_else = ui.input(|i| i.pointer.any_pressed()) && !self.any_hovered;
|
||||||
let delected_everything = pressed_escape || clicked_something_else;
|
let delected_everything = pressed_escape || clicked_something_else;
|
||||||
|
|
||||||
if delected_everything {
|
if delected_everything {
|
||||||
self.selection = None;
|
self.selection = None;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ctx.input(|i| i.pointer.any_released()) {
|
if ui.input(|i| i.pointer.any_released()) {
|
||||||
self.is_dragging = false;
|
self.is_dragging = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
let text_to_copy = std::mem::take(&mut self.text_to_copy);
|
let text_to_copy = std::mem::take(&mut self.text_to_copy);
|
||||||
if !text_to_copy.is_empty() {
|
if !text_to_copy.is_empty() {
|
||||||
ctx.copy_text(text_to_copy);
|
ui.copy_text(text_to_copy);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -73,7 +73,7 @@ use std::sync::Arc;
|
|||||||
|
|
||||||
use epaint::{Pos2, Vec2};
|
use epaint::{Pos2, Vec2};
|
||||||
|
|
||||||
use crate::{Context, Id};
|
use crate::{Context, Id, Ui};
|
||||||
|
|
||||||
// ----------------------------------------------------------------------------
|
// ----------------------------------------------------------------------------
|
||||||
|
|
||||||
@@ -263,7 +263,7 @@ impl ViewportIdPair {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// The user-code that shows the ui in the viewport, used for deferred viewports.
|
/// The user-code that shows the ui in the viewport, used for deferred viewports.
|
||||||
pub type DeferredViewportUiCallback = dyn Fn(&Context) + Sync + Send;
|
pub type DeferredViewportUiCallback = dyn Fn(&mut Ui) + Sync + Send;
|
||||||
|
|
||||||
/// Render the given viewport, calling the given ui callback.
|
/// Render the given viewport, calling the given ui callback.
|
||||||
pub type ImmediateViewportRendererCallback = dyn for<'a> Fn(&Context, ImmediateViewport<'a>);
|
pub type ImmediateViewportRendererCallback = dyn for<'a> Fn(&Context, ImmediateViewport<'a>);
|
||||||
@@ -1251,5 +1251,5 @@ pub struct ImmediateViewport<'a> {
|
|||||||
pub builder: ViewportBuilder,
|
pub builder: ViewportBuilder,
|
||||||
|
|
||||||
/// The user-code that shows the GUI.
|
/// The user-code that shows the GUI.
|
||||||
pub viewport_ui_cb: Box<dyn FnMut(&Context) + 'a>,
|
pub viewport_ui_cb: Box<dyn FnMut(&mut Ui) + 'a>,
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,11 +5,11 @@ use accesskit_consumer::{FilterResult, Node, Tree, TreeChangeHandler};
|
|||||||
|
|
||||||
use eframe::epaint::text::TextWrapMode;
|
use eframe::epaint::text::TextWrapMode;
|
||||||
use egui::{
|
use egui::{
|
||||||
Button, Color32, Context, Event, Frame, FullOutput, Id, Key, KeyboardShortcut, Label,
|
Button, Color32, Event, Frame, FullOutput, Id, Key, KeyboardShortcut, Label, Modifiers, Panel,
|
||||||
Modifiers, Panel, RawInput, RichText, ScrollArea, Ui, collapsing_header::CollapsingState,
|
RawInput, RichText, ScrollArea, Ui, collapsing_header::CollapsingState,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// This [`egui::Plugin`] adds an inspector Panel.
|
/// This [`egui::Plugin`] adds an inspector panel.
|
||||||
///
|
///
|
||||||
/// It can be opened with the `(Cmd/Ctrl)+Alt+I`. It shows the current AccessKit tree and details
|
/// It can be opened with the `(Cmd/Ctrl)+Alt+I`. It shows the current AccessKit tree and details
|
||||||
/// for the selected node.
|
/// for the selected node.
|
||||||
@@ -71,8 +71,8 @@ impl egui::Plugin for AccessibilityInspectorPlugin {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_begin_pass(&mut self, ctx: &Context) {
|
fn on_begin_pass(&mut self, ui: &mut Ui) {
|
||||||
if ctx.input_mut(|i| {
|
if ui.input_mut(|i| {
|
||||||
i.consume_shortcut(&KeyboardShortcut::new(
|
i.consume_shortcut(&KeyboardShortcut::new(
|
||||||
Modifiers::COMMAND | Modifiers::ALT,
|
Modifiers::COMMAND | Modifiers::ALT,
|
||||||
Key::I,
|
Key::I,
|
||||||
@@ -85,9 +85,9 @@ impl egui::Plugin for AccessibilityInspectorPlugin {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx.enable_accesskit();
|
ui.enable_accesskit();
|
||||||
|
|
||||||
Panel::right(Self::id()).show(ctx, |ui| {
|
Panel::right(Self::id()).show_inside(ui, |ui| {
|
||||||
ui.heading("🔎 AccessKit Inspector");
|
ui.heading("🔎 AccessKit Inspector");
|
||||||
if let Some(selected_node) = self.selected_node {
|
if let Some(selected_node) = self.selected_node {
|
||||||
Panel::bottom(Self::id().with("details_panel"))
|
Panel::bottom(Self::id().with("details_panel"))
|
||||||
|
|||||||
@@ -271,7 +271,7 @@ impl eframe::App for WrapApp {
|
|||||||
color.to_normalized_gamma_f32()
|
color.to_normalized_gamma_f32()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update(&mut self, ctx: &egui::Context, frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, frame: &mut eframe::Frame) {
|
||||||
#[cfg(target_arch = "wasm32")]
|
#[cfg(target_arch = "wasm32")]
|
||||||
if let Some(anchor) = frame
|
if let Some(anchor) = frame
|
||||||
.info()
|
.info()
|
||||||
@@ -285,36 +285,36 @@ impl eframe::App for WrapApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(target_arch = "wasm32"))]
|
#[cfg(not(target_arch = "wasm32"))]
|
||||||
if ctx.input_mut(|i| i.consume_key(egui::Modifiers::NONE, egui::Key::F11)) {
|
if ui.input_mut(|i| i.consume_key(egui::Modifiers::NONE, egui::Key::F11)) {
|
||||||
let fullscreen = ctx.input(|i| i.viewport().fullscreen.unwrap_or(false));
|
let fullscreen = ui.input(|i| i.viewport().fullscreen.unwrap_or(false));
|
||||||
ctx.send_viewport_cmd(egui::ViewportCommand::Fullscreen(!fullscreen));
|
ui.send_viewport_cmd(egui::ViewportCommand::Fullscreen(!fullscreen));
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut cmd = Command::Nothing;
|
let mut cmd = Command::Nothing;
|
||||||
egui::Panel::top("wrap_app_top_bar")
|
egui::Panel::top("wrap_app_top_bar")
|
||||||
.frame(egui::Frame::new().inner_margin(4))
|
.frame(egui::Frame::new().inner_margin(4))
|
||||||
.show(ctx, |ui| {
|
.show_inside(ui, |ui| {
|
||||||
ui.horizontal_wrapped(|ui| {
|
ui.horizontal_wrapped(|ui| {
|
||||||
ui.visuals_mut().button_frame = false;
|
ui.visuals_mut().button_frame = false;
|
||||||
self.bar_contents(ui, frame, &mut cmd);
|
self.bar_contents(ui, frame, &mut cmd);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
self.state.backend_panel.update(ctx, frame);
|
self.state.backend_panel.update(ui.ctx(), frame);
|
||||||
|
|
||||||
egui::CentralPanel::no_frame().show(ctx, |ui| {
|
egui::CentralPanel::no_frame().show_inside(ui, |ui| {
|
||||||
if !is_mobile(ctx) {
|
if !is_mobile(ui.ctx()) {
|
||||||
cmd = self.backend_panel(ui, frame);
|
cmd = self.backend_panel(ui, frame);
|
||||||
}
|
}
|
||||||
|
|
||||||
self.show_selected_app(ui, frame);
|
self.show_selected_app(ui, frame);
|
||||||
});
|
});
|
||||||
|
|
||||||
self.state.backend_panel.end_of_frame(ctx);
|
self.state.backend_panel.end_of_frame(ui.ctx());
|
||||||
|
|
||||||
self.ui_file_drag_and_drop(ctx);
|
self.ui_file_drag_and_drop(ui.ctx());
|
||||||
|
|
||||||
self.run_cmd(ctx, cmd);
|
self.run_cmd(ui.ctx(), cmd);
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "glow")]
|
#[cfg(feature = "glow")]
|
||||||
|
|||||||
@@ -66,10 +66,10 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
|
|
||||||
{
|
{
|
||||||
let ctx = egui::Context::default();
|
let ctx = egui::Context::default();
|
||||||
let _ = ctx.run(RawInput::default(), |ctx| {
|
let _ = ctx.run_ui(RawInput::default(), |ui| {
|
||||||
c.bench_function("label &str", |b| {
|
c.bench_function("label &str", |b| {
|
||||||
b.iter_batched_ref(
|
b.iter_batched_ref(
|
||||||
|| create_benchmark_ui(ctx),
|
|| create_benchmark_ui(ui),
|
||||||
|ui| {
|
|ui| {
|
||||||
ui.label("the quick brown fox jumps over the lazy dog");
|
ui.label("the quick brown fox jumps over the lazy dog");
|
||||||
},
|
},
|
||||||
@@ -78,7 +78,7 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
});
|
});
|
||||||
c.bench_function("label format!", |b| {
|
c.bench_function("label format!", |b| {
|
||||||
b.iter_batched_ref(
|
b.iter_batched_ref(
|
||||||
|| create_benchmark_ui(ctx),
|
|| create_benchmark_ui(ui),
|
||||||
|ui| {
|
|ui| {
|
||||||
ui.label("the quick brown fox jumps over the lazy dog".to_owned());
|
ui.label("the quick brown fox jumps over the lazy dog".to_owned());
|
||||||
},
|
},
|
||||||
@@ -90,7 +90,7 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
|
|
||||||
{
|
{
|
||||||
let ctx = egui::Context::default();
|
let ctx = egui::Context::default();
|
||||||
let _ = ctx.run(RawInput::default(), |ctx| {
|
let _ = ctx.run_ui(RawInput::default(), |ui| {
|
||||||
let mut group = c.benchmark_group("button");
|
let mut group = c.benchmark_group("button");
|
||||||
|
|
||||||
// To ensure we have a valid image, let's use the font texture. The size
|
// To ensure we have a valid image, let's use the font texture. The size
|
||||||
@@ -99,7 +99,7 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
|
|
||||||
group.bench_function("1_button_text", |b| {
|
group.bench_function("1_button_text", |b| {
|
||||||
b.iter_batched_ref(
|
b.iter_batched_ref(
|
||||||
|| create_benchmark_ui(ctx),
|
|| create_benchmark_ui(ui),
|
||||||
|ui| {
|
|ui| {
|
||||||
ui.add(Button::new("Hello World"));
|
ui.add(Button::new("Hello World"));
|
||||||
},
|
},
|
||||||
@@ -108,7 +108,7 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
});
|
});
|
||||||
group.bench_function("2_button_text_image", |b| {
|
group.bench_function("2_button_text_image", |b| {
|
||||||
b.iter_batched_ref(
|
b.iter_batched_ref(
|
||||||
|| create_benchmark_ui(ctx),
|
|| create_benchmark_ui(ui),
|
||||||
|ui| {
|
|ui| {
|
||||||
ui.add(Button::image_and_text(image, "Hello World"));
|
ui.add(Button::image_and_text(image, "Hello World"));
|
||||||
},
|
},
|
||||||
@@ -117,7 +117,7 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
});
|
});
|
||||||
group.bench_function("3_button_text_image_right_text", |b| {
|
group.bench_function("3_button_text_image_right_text", |b| {
|
||||||
b.iter_batched_ref(
|
b.iter_batched_ref(
|
||||||
|| create_benchmark_ui(ctx),
|
|| create_benchmark_ui(ui),
|
||||||
|ui| {
|
|ui| {
|
||||||
ui.add(Button::image_and_text(image, "Hello World").right_text("⏵"));
|
ui.add(Button::image_and_text(image, "Hello World").right_text("⏵"));
|
||||||
},
|
},
|
||||||
@@ -126,7 +126,7 @@ pub fn criterion_benchmark(c: &mut Criterion) {
|
|||||||
});
|
});
|
||||||
group.bench_function("4_button_italic", |b| {
|
group.bench_function("4_button_italic", |b| {
|
||||||
b.iter_batched_ref(
|
b.iter_batched_ref(
|
||||||
|| create_benchmark_ui(ctx),
|
|| create_benchmark_ui(ui),
|
||||||
|ui| {
|
|ui| {
|
||||||
ui.add(Button::new(RichText::new("Hello World").italics()));
|
ui.add(Button::new(RichText::new("Hello World").italics()));
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -372,7 +372,7 @@ fn file_menu_button(ui: &mut Ui) {
|
|||||||
mod tests {
|
mod tests {
|
||||||
use crate::{Demo as _, demo::demo_app_windows::DemoGroups};
|
use crate::{Demo as _, demo::demo_app_windows::DemoGroups};
|
||||||
|
|
||||||
use egui_kittest::kittest::{NodeT as _, Queryable as _};
|
use egui_kittest::kittest::Queryable as _;
|
||||||
use egui_kittest::{Harness, OsThreshold, SnapshotOptions, SnapshotResults};
|
use egui_kittest::{Harness, OsThreshold, SnapshotOptions, SnapshotResults};
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
@@ -394,12 +394,15 @@ mod tests {
|
|||||||
|
|
||||||
let name = remove_leading_emoji(demo.name());
|
let name = remove_leading_emoji(demo.name());
|
||||||
|
|
||||||
let mut harness = Harness::new(|ctx| {
|
let mut harness = Harness::new_ui(|ui| {
|
||||||
egui_extras::install_image_loaders(ctx);
|
egui_extras::install_image_loaders(ui);
|
||||||
demo.show(ctx, &mut true);
|
demo.show(ui, &mut true);
|
||||||
});
|
});
|
||||||
|
|
||||||
let window = harness.queryable_node().children().next().unwrap();
|
let window = harness
|
||||||
|
.get_all_by_role(egui::accesskit::Role::Window)
|
||||||
|
.next()
|
||||||
|
.unwrap();
|
||||||
// TODO(lucasmerlin): Windows should probably have a label?
|
// TODO(lucasmerlin): Windows should probably have a label?
|
||||||
//let window = harness.get_by_label(name);
|
//let window = harness.get_by_label(name);
|
||||||
|
|
||||||
|
|||||||
@@ -176,9 +176,9 @@ mod tests {
|
|||||||
..Modals::default()
|
..Modals::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut harness = Harness::new_state(
|
let mut harness = Harness::new_ui_state(
|
||||||
|ctx, modals| {
|
|ui, modals| {
|
||||||
modals.show(ctx, &mut true);
|
modals.show(ui, &mut true);
|
||||||
},
|
},
|
||||||
initial_state,
|
initial_state,
|
||||||
);
|
);
|
||||||
@@ -204,9 +204,9 @@ mod tests {
|
|||||||
..Modals::default()
|
..Modals::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut harness = Harness::new_state(
|
let mut harness = Harness::new_ui_state(
|
||||||
|ctx, modals| {
|
|ui, modals| {
|
||||||
modals.show(ctx, &mut true);
|
modals.show(ui, &mut true);
|
||||||
},
|
},
|
||||||
initial_state,
|
initial_state,
|
||||||
);
|
);
|
||||||
@@ -228,9 +228,9 @@ mod tests {
|
|||||||
..Modals::default()
|
..Modals::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut harness = Harness::new_state(
|
let mut harness = Harness::new_ui_state(
|
||||||
|ctx, modals| {
|
|ui, modals| {
|
||||||
modals.show(ctx, &mut true);
|
modals.show(ui, &mut true);
|
||||||
},
|
},
|
||||||
initial_state,
|
initial_state,
|
||||||
);
|
);
|
||||||
@@ -258,9 +258,9 @@ mod tests {
|
|||||||
..Modals::default()
|
..Modals::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut harness = Harness::new_state(
|
let mut harness = Harness::new_ui_state(
|
||||||
|ctx, modals| {
|
|ui, modals| {
|
||||||
modals.show(ctx, &mut true);
|
modals.show(ui, &mut true);
|
||||||
},
|
},
|
||||||
initial_state,
|
initial_state,
|
||||||
);
|
);
|
||||||
|
|||||||
@@ -120,9 +120,9 @@ mod tests {
|
|||||||
#[test]
|
#[test]
|
||||||
pub fn should_type() {
|
pub fn should_type() {
|
||||||
let text = "Hello, world!".to_owned();
|
let text = "Hello, world!".to_owned();
|
||||||
let mut harness = Harness::new_state(
|
let mut harness = Harness::new_ui_state(
|
||||||
move |ctx, text| {
|
move |ui, text| {
|
||||||
CentralPanel::default().show(ctx, |ui| {
|
CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.text_edit_singleline(text);
|
ui.text_edit_singleline(text);
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -215,10 +215,11 @@ impl winit::application::ApplicationHandler<UserEvent> for GlowApp {
|
|||||||
let mut redraw = || {
|
let mut redraw = || {
|
||||||
let mut quit = false;
|
let mut quit = false;
|
||||||
|
|
||||||
self.egui_glow.as_mut().unwrap().run(
|
self.egui_glow
|
||||||
self.gl_window.as_mut().unwrap().window(),
|
.as_mut()
|
||||||
|egui_ctx| {
|
.unwrap()
|
||||||
egui::Panel::left("my_side_panel").show(egui_ctx, |ui| {
|
.run(self.gl_window.as_mut().unwrap().window(), |ui| {
|
||||||
|
egui::Panel::left("my_side_panel").show_inside(ui, |ui| {
|
||||||
ui.heading("Hello World!");
|
ui.heading("Hello World!");
|
||||||
if ui.button("Quit").clicked() {
|
if ui.button("Quit").clicked() {
|
||||||
quit = true;
|
quit = true;
|
||||||
@@ -226,8 +227,7 @@ impl winit::application::ApplicationHandler<UserEvent> for GlowApp {
|
|||||||
|
|
||||||
ui.color_edit_button_rgb(self.clear_color.as_mut().try_into().unwrap());
|
ui.color_edit_button_rgb(self.clear_color.as_mut().try_into().unwrap());
|
||||||
});
|
});
|
||||||
},
|
});
|
||||||
);
|
|
||||||
|
|
||||||
if quit {
|
if quit {
|
||||||
event_loop.exit();
|
event_loop.exit();
|
||||||
|
|||||||
@@ -65,7 +65,7 @@ impl EguiGlow {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Call [`Self::paint`] later to paint.
|
/// Call [`Self::paint`] later to paint.
|
||||||
pub fn run(&mut self, window: &winit::window::Window, run_ui: impl FnMut(&egui::Context)) {
|
pub fn run(&mut self, window: &winit::window::Window, run_ui: impl FnMut(&mut egui::Ui)) {
|
||||||
let raw_input = self.egui_winit.take_egui_input(window);
|
let raw_input = self.egui_winit.take_egui_input(window);
|
||||||
|
|
||||||
let egui::FullOutput {
|
let egui::FullOutput {
|
||||||
@@ -74,7 +74,7 @@ impl EguiGlow {
|
|||||||
shapes,
|
shapes,
|
||||||
pixels_per_point,
|
pixels_per_point,
|
||||||
viewport_output,
|
viewport_output,
|
||||||
} = self.egui_ctx.run(raw_input, run_ui);
|
} = self.egui_ctx.run_ui(raw_input, run_ui);
|
||||||
|
|
||||||
if viewport_output.len() > 1 {
|
if viewport_output.len() > 1 {
|
||||||
log::warn!("Multiple viewports not yet supported by EguiGlow");
|
log::warn!("Multiple viewports not yet supported by EguiGlow");
|
||||||
|
|||||||
@@ -24,58 +24,60 @@ pub(crate) enum AppKind<'a, State> {
|
|||||||
impl<State> AppKind<'_, State> {
|
impl<State> AppKind<'_, State> {
|
||||||
pub fn run(
|
pub fn run(
|
||||||
&mut self,
|
&mut self,
|
||||||
ctx: &egui::Context,
|
ui: &mut egui::Ui,
|
||||||
state: &mut State,
|
state: &mut State,
|
||||||
sizing_pass: bool,
|
sizing_pass: bool,
|
||||||
) -> Option<egui::Response> {
|
) -> Option<egui::Response> {
|
||||||
match self {
|
match self {
|
||||||
AppKind::Context(f) => {
|
AppKind::Context(f) => {
|
||||||
debug_assert!(!sizing_pass, "Context closures cannot do a sizing pass");
|
debug_assert!(!sizing_pass, "Context closures cannot do a sizing pass");
|
||||||
f(ctx);
|
f(ui);
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
AppKind::ContextState(f) => {
|
AppKind::ContextState(f) => {
|
||||||
debug_assert!(!sizing_pass, "Context closures cannot do a sizing pass");
|
debug_assert!(!sizing_pass, "Context closures cannot do a sizing pass");
|
||||||
f(ctx, state);
|
f(ui, state);
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
#[cfg(feature = "eframe")]
|
#[cfg(feature = "eframe")]
|
||||||
AppKind::Eframe((get_app, frame)) => {
|
AppKind::Eframe((get_app, frame)) => {
|
||||||
let app = get_app(state);
|
let app = get_app(state);
|
||||||
app.update(ctx, frame);
|
|
||||||
|
app.logic(ui, frame);
|
||||||
|
|
||||||
|
#[expect(deprecated)]
|
||||||
|
app.update(ui, frame);
|
||||||
|
|
||||||
|
app.ui(ui, frame);
|
||||||
|
|
||||||
None
|
None
|
||||||
}
|
}
|
||||||
kind_ui => Some(kind_ui.run_ui(ctx, state, sizing_pass)),
|
kind_ui => Some(kind_ui.run_ui(ui, state, sizing_pass)),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn run_ui(
|
fn run_ui(
|
||||||
&mut self,
|
&mut self,
|
||||||
ctx: &egui::Context,
|
ui: &mut egui::Ui,
|
||||||
state: &mut State,
|
state: &mut State,
|
||||||
sizing_pass: bool,
|
sizing_pass: bool,
|
||||||
) -> egui::Response {
|
) -> egui::Response {
|
||||||
egui::CentralPanel::default()
|
let mut builder = egui::UiBuilder::new();
|
||||||
.frame(Frame::NONE)
|
if sizing_pass {
|
||||||
.show(ctx, |ui| {
|
builder.sizing_pass = true;
|
||||||
let mut builder = egui::UiBuilder::new();
|
}
|
||||||
if sizing_pass {
|
ui.scope_builder(builder, |ui| {
|
||||||
builder.sizing_pass = true;
|
Frame::central_panel(ui.style())
|
||||||
}
|
.outer_margin(8.0)
|
||||||
ui.scope_builder(builder, |ui| {
|
.inner_margin(0.0)
|
||||||
Frame::central_panel(ui.style())
|
.show(ui, |ui| match self {
|
||||||
.outer_margin(8.0)
|
AppKind::Ui(f) => f(ui),
|
||||||
.inner_margin(0.0)
|
AppKind::UiState(f) => f(ui, state),
|
||||||
.show(ui, |ui| match self {
|
_ => unreachable!(
|
||||||
AppKind::Ui(f) => f(ui),
|
"run_ui should only be called with AppKind::Ui or AppKind UiState"
|
||||||
AppKind::UiState(f) => f(ui, state),
|
),
|
||||||
_ => unreachable!(
|
});
|
||||||
"run_ui should only be called with AppKind::Ui or AppKind UiState"
|
})
|
||||||
),
|
.response
|
||||||
});
|
|
||||||
})
|
|
||||||
.response
|
|
||||||
})
|
|
||||||
.inner
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -167,6 +167,7 @@ impl<State> HarnessBuilder<State> {
|
|||||||
/// assert_eq!(*harness.state(), true);
|
/// assert_eq!(*harness.state(), true);
|
||||||
/// ```
|
/// ```
|
||||||
#[track_caller]
|
#[track_caller]
|
||||||
|
#[deprecated = "use `build_ui_state` instead"]
|
||||||
pub fn build_state<'a>(
|
pub fn build_state<'a>(
|
||||||
self,
|
self,
|
||||||
app: impl FnMut(&egui::Context, &mut State) + 'a,
|
app: impl FnMut(&egui::Context, &mut State) + 'a,
|
||||||
@@ -251,6 +252,7 @@ impl HarnessBuilder {
|
|||||||
/// ```
|
/// ```
|
||||||
#[must_use]
|
#[must_use]
|
||||||
#[track_caller]
|
#[track_caller]
|
||||||
|
#[deprecated = "use `build_ui` instead"]
|
||||||
pub fn build<'a>(self, app: impl FnMut(&egui::Context) + 'a) -> Harness<'a> {
|
pub fn build<'a>(self, app: impl FnMut(&egui::Context) + 'a) -> Harness<'a> {
|
||||||
Harness::from_builder(self, AppKind::Context(Box::new(app)), (), None)
|
Harness::from_builder(self, AppKind::Context(Box::new(app)), (), None)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -137,8 +137,8 @@ impl<'a, State> Harness<'a, State> {
|
|||||||
|
|
||||||
// We need to run egui for a single frame so that the AccessKit state can be initialized
|
// We need to run egui for a single frame so that the AccessKit state can be initialized
|
||||||
// and users can immediately start querying for widgets.
|
// and users can immediately start querying for widgets.
|
||||||
let mut output = ctx.run(input.clone(), |ctx| {
|
let mut output = ctx.run_ui(input.clone(), |ui| {
|
||||||
response = app.run(ctx, &mut state, false);
|
response = app.run(ui, &mut state, false);
|
||||||
});
|
});
|
||||||
|
|
||||||
renderer.handle_delta(&output.textures_delta);
|
renderer.handle_delta(&output.textures_delta);
|
||||||
@@ -204,7 +204,9 @@ impl<'a, State> Harness<'a, State> {
|
|||||||
/// assert_eq!(*harness.state(), true);
|
/// assert_eq!(*harness.state(), true);
|
||||||
/// ```
|
/// ```
|
||||||
#[track_caller]
|
#[track_caller]
|
||||||
|
#[deprecated = "use `new_ui_state` instead"]
|
||||||
pub fn new_state(app: impl FnMut(&egui::Context, &mut State) + 'a, state: State) -> Self {
|
pub fn new_state(app: impl FnMut(&egui::Context, &mut State) + 'a, state: State) -> Self {
|
||||||
|
#[expect(deprecated)]
|
||||||
Self::builder().build_state(app, state)
|
Self::builder().build_state(app, state)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -287,8 +289,8 @@ impl<'a, State> Harness<'a, State> {
|
|||||||
fn _step(&mut self, sizing_pass: bool) {
|
fn _step(&mut self, sizing_pass: bool) {
|
||||||
self.input.predicted_dt = self.step_dt;
|
self.input.predicted_dt = self.step_dt;
|
||||||
|
|
||||||
let mut output = self.ctx.run(self.input.take(), |ctx| {
|
let mut output = self.ctx.run_ui(self.input.take(), |ui| {
|
||||||
self.response = self.app.run(ctx, &mut self.state, sizing_pass);
|
self.response = self.app.run(ui, &mut self.state, sizing_pass);
|
||||||
});
|
});
|
||||||
self.kittest.update(
|
self.kittest.update(
|
||||||
output
|
output
|
||||||
@@ -735,7 +737,9 @@ impl<'a> Harness<'a> {
|
|||||||
/// });
|
/// });
|
||||||
/// ```
|
/// ```
|
||||||
#[track_caller]
|
#[track_caller]
|
||||||
|
#[deprecated = "use `new_ui` instead"]
|
||||||
pub fn new(app: impl FnMut(&egui::Context) + 'a) -> Self {
|
pub fn new(app: impl FnMut(&egui::Context) + 'a) -> Self {
|
||||||
|
#[expect(deprecated)]
|
||||||
Self::builder().build(app)
|
Self::builder().build(app)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
//! Tests the accesskit accessibility output of egui.
|
//! Tests the accesskit accessibility output of egui.
|
||||||
|
|
||||||
use egui::{
|
use egui::{
|
||||||
CentralPanel, Context, RawInput, Window,
|
CentralPanel, Context, RawInput, Ui, Window,
|
||||||
accesskit::{NodeId, Role, TreeUpdate},
|
accesskit::{NodeId, Role, TreeUpdate},
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -12,8 +12,8 @@ use egui::{
|
|||||||
/// are put there because of the widgets rendered.
|
/// are put there because of the widgets rendered.
|
||||||
#[test]
|
#[test]
|
||||||
fn empty_ui_should_return_tree_with_only_root_window() {
|
fn empty_ui_should_return_tree_with_only_root_window() {
|
||||||
let output = accesskit_output_single_egui_frame(|ctx| {
|
let output = accesskit_output_single_egui_frame(|_ui| {
|
||||||
CentralPanel::default().show(ctx, |_| {});
|
// Nothing here beyond the default empty UI
|
||||||
});
|
});
|
||||||
|
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
@@ -42,8 +42,8 @@ fn empty_ui_should_return_tree_with_only_root_window() {
|
|||||||
fn button_node() {
|
fn button_node() {
|
||||||
let button_text = "This is a test button!";
|
let button_text = "This is a test button!";
|
||||||
|
|
||||||
let output = accesskit_output_single_egui_frame(|ctx| {
|
let output = accesskit_output_single_egui_frame(|ui| {
|
||||||
CentralPanel::default().show(ctx, |ui| ui.button(button_text));
|
CentralPanel::default().show_inside(ui, |ui| ui.button(button_text));
|
||||||
});
|
});
|
||||||
|
|
||||||
let (_, button) = output
|
let (_, button) = output
|
||||||
@@ -60,8 +60,8 @@ fn button_node() {
|
|||||||
fn disabled_button_node() {
|
fn disabled_button_node() {
|
||||||
let button_text = "This is a test button!";
|
let button_text = "This is a test button!";
|
||||||
|
|
||||||
let output = accesskit_output_single_egui_frame(|ctx| {
|
let output = accesskit_output_single_egui_frame(|ui| {
|
||||||
CentralPanel::default().show(ctx, |ui| {
|
CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.add_enabled(false, egui::Button::new(button_text))
|
ui.add_enabled(false, egui::Button::new(button_text))
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -81,8 +81,8 @@ fn toggle_button_node() {
|
|||||||
let button_text = "A toggle button";
|
let button_text = "A toggle button";
|
||||||
|
|
||||||
let mut selected = false;
|
let mut selected = false;
|
||||||
let output = accesskit_output_single_egui_frame(|ctx| {
|
let output = accesskit_output_single_egui_frame(|ui| {
|
||||||
CentralPanel::default().show(ctx, |ui| ui.toggle_value(&mut selected, button_text));
|
CentralPanel::default().show_inside(ui, |ui| ui.toggle_value(&mut selected, button_text));
|
||||||
});
|
});
|
||||||
|
|
||||||
let (_, toggle) = output
|
let (_, toggle) = output
|
||||||
@@ -97,8 +97,8 @@ fn toggle_button_node() {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn multiple_disabled_widgets() {
|
fn multiple_disabled_widgets() {
|
||||||
let output = accesskit_output_single_egui_frame(|ctx| {
|
let output = accesskit_output_single_egui_frame(|ui| {
|
||||||
CentralPanel::default().show(ctx, |ui| {
|
CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.add_enabled_ui(false, |ui| {
|
ui.add_enabled_ui(false, |ui| {
|
||||||
let _ = ui.button("Button 1");
|
let _ = ui.button("Button 1");
|
||||||
let _ = ui.button("Button 2");
|
let _ = ui.button("Button 2");
|
||||||
@@ -120,12 +120,12 @@ fn multiple_disabled_widgets() {
|
|||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn window_children() {
|
fn window_children() {
|
||||||
let output = accesskit_output_single_egui_frame(|ctx| {
|
let output = accesskit_output_single_egui_frame(|ui| {
|
||||||
let mut open = true;
|
let mut open = true;
|
||||||
Window::new("test window")
|
Window::new("test window")
|
||||||
.open(&mut open)
|
.open(&mut open)
|
||||||
.resizable(false)
|
.resizable(false)
|
||||||
.show(ctx, |ui| {
|
.show(ui.ctx(), |ui| {
|
||||||
let _ = ui.button("A button");
|
let _ = ui.button("A button");
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -138,13 +138,13 @@ fn window_children() {
|
|||||||
assert_button_exists(&output, "Hide", window_id);
|
assert_button_exists(&output, "Hide", window_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn accesskit_output_single_egui_frame(run_ui: impl FnMut(&Context)) -> TreeUpdate {
|
fn accesskit_output_single_egui_frame(run_ui: impl FnMut(&mut Ui)) -> TreeUpdate {
|
||||||
let ctx = Context::default();
|
let ctx = Context::default();
|
||||||
// Disable animations, so we do not need to wait for animations to end to see the result.
|
// Disable animations, so we do not need to wait for animations to end to see the result.
|
||||||
ctx.global_style_mut(|style| style.animation_time = 0.0);
|
ctx.global_style_mut(|style| style.animation_time = 0.0);
|
||||||
ctx.enable_accesskit();
|
ctx.enable_accesskit();
|
||||||
|
|
||||||
let output = ctx.run(RawInput::default(), run_ui);
|
let output = ctx.run_ui(RawInput::default(), run_ui);
|
||||||
|
|
||||||
output
|
output
|
||||||
.platform_output
|
.platform_output
|
||||||
|
|||||||
@@ -23,16 +23,16 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("Try to close the window");
|
ui.heading("Try to close the window");
|
||||||
});
|
});
|
||||||
|
|
||||||
if ctx.input(|i| i.viewport().close_requested()) {
|
if ui.input(|i| i.viewport().close_requested()) {
|
||||||
if self.allowed_to_close {
|
if self.allowed_to_close {
|
||||||
// do nothing - we will close
|
// do nothing - we will close
|
||||||
} else {
|
} else {
|
||||||
ctx.send_viewport_cmd(egui::ViewportCommand::CancelClose);
|
ui.send_viewport_cmd(egui::ViewportCommand::CancelClose);
|
||||||
self.show_confirmation_dialog = true;
|
self.show_confirmation_dialog = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -41,7 +41,7 @@ impl eframe::App for MyApp {
|
|||||||
egui::Window::new("Do you want to quit?")
|
egui::Window::new("Do you want to quit?")
|
||||||
.collapsible(false)
|
.collapsible(false)
|
||||||
.resizable(false)
|
.resizable(false)
|
||||||
.show(ctx, |ui| {
|
.show(ui.ctx(), |ui| {
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
if ui.button("No").clicked() {
|
if ui.button("No").clicked() {
|
||||||
self.show_confirmation_dialog = false;
|
self.show_confirmation_dialog = false;
|
||||||
|
|||||||
@@ -43,8 +43,8 @@ impl MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
ui.spacing_mut().item_spacing.x = 0.0;
|
ui.spacing_mut().item_spacing.x = 0.0;
|
||||||
ui.label("The triangle is being painted using ");
|
ui.label("The triangle is being painted using ");
|
||||||
|
|||||||
@@ -86,8 +86,8 @@ impl MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("egui using custom fonts");
|
ui.heading("egui using custom fonts");
|
||||||
ui.text_edit_multiline(&mut self.text);
|
ui.text_edit_multiline(&mut self.text);
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -65,8 +65,8 @@ impl MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, content);
|
egui::CentralPanel::default().show_inside(ui, content);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -44,11 +44,11 @@ impl Default for MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::Window::new("Custom Keypad")
|
egui::Window::new("Custom Keypad")
|
||||||
.default_pos([100.0, 100.0])
|
.default_pos([100.0, 100.0])
|
||||||
.title_bar(true)
|
.title_bar(true)
|
||||||
.show(ctx, |ui| {
|
.show(ui.ctx(), |ui| {
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
ui.label("Your name: ");
|
ui.label("Your name: ");
|
||||||
ui.text_edit_singleline(&mut self.name);
|
ui.text_edit_singleline(&mut self.name);
|
||||||
@@ -60,7 +60,7 @@ impl eframe::App for MyApp {
|
|||||||
ui.label(format!("Hello '{}', age {}", self.name, self.age));
|
ui.label(format!("Hello '{}', age {}", self.name, self.age));
|
||||||
});
|
});
|
||||||
|
|
||||||
self.keypad.show(ctx);
|
self.keypad.show(ui.ctx());
|
||||||
}
|
}
|
||||||
|
|
||||||
fn raw_input_hook(&mut self, ctx: &egui::Context, raw_input: &mut egui::RawInput) {
|
fn raw_input_hook(&mut self, ctx: &egui::Context, raw_input: &mut egui::RawInput) {
|
||||||
|
|||||||
@@ -57,8 +57,8 @@ impl MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("egui using a customized style");
|
ui.heading("egui using a customized style");
|
||||||
ui.label("Switch between dark and light mode to see the different styles in action.");
|
ui.label("Switch between dark and light mode to see the different styles in action.");
|
||||||
global_theme_preference_buttons(ui);
|
global_theme_preference_buttons(ui);
|
||||||
|
|||||||
@@ -31,8 +31,8 @@ impl eframe::App for MyApp {
|
|||||||
egui::Rgba::TRANSPARENT.to_array() // Make sure we don't paint anything behind the rounded corners
|
egui::Rgba::TRANSPARENT.to_array() // Make sure we don't paint anything behind the rounded corners
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
custom_window_frame(ctx, "egui with custom frame", |ui| {
|
custom_window_frame(ui.ctx(), "egui with custom frame", |ui| {
|
||||||
ui.label("This is just the contents of the window.");
|
ui.label("This is just the contents of the window.");
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
ui.label("egui theme:");
|
ui.label("egui theme:");
|
||||||
|
|||||||
@@ -44,8 +44,8 @@ impl Default for MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("My External Eventloop Application");
|
ui.heading("My External Eventloop Application");
|
||||||
|
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
@@ -82,7 +82,7 @@ impl eframe::App for MyApp {
|
|||||||
ui.label("Blinky!");
|
ui.label("Blinky!");
|
||||||
});
|
});
|
||||||
|
|
||||||
ctx.request_repaint_after_secs((0.5 - (now % 0.5)) as f32);
|
ui.request_repaint_after_secs((0.5 - (now % 0.5)) as f32);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -76,8 +76,8 @@ impl Default for MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("My External Eventloop Application");
|
ui.heading("My External Eventloop Application");
|
||||||
|
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
@@ -86,7 +86,7 @@ impl eframe::App for MyApp {
|
|||||||
}
|
}
|
||||||
if ui.button("Increment Later").clicked() {
|
if ui.button("Increment Later").clicked() {
|
||||||
let value = self.value.clone();
|
let value = self.value.clone();
|
||||||
let ctx = ctx.clone();
|
let ctx = ui.ctx().clone();
|
||||||
tokio::task::spawn_local(async move {
|
tokio::task::spawn_local(async move {
|
||||||
tokio::time::sleep(Duration::from_secs(1)).await;
|
tokio::time::sleep(Duration::from_secs(1)).await;
|
||||||
value.set(value.get() + 1);
|
value.set(value.get() + 1);
|
||||||
@@ -123,7 +123,7 @@ impl eframe::App for MyApp {
|
|||||||
ui.label("Blinky!");
|
ui.label("Blinky!");
|
||||||
});
|
});
|
||||||
|
|
||||||
ctx.request_repaint_after_secs((0.5 - (now % 0.5)) as f32);
|
ui.request_repaint_after_secs((0.5 - (now % 0.5)) as f32);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -25,8 +25,8 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.label("Drag-and-drop files onto the window!");
|
ui.label("Drag-and-drop files onto the window!");
|
||||||
|
|
||||||
if ui.button("Open file…").clicked()
|
if ui.button("Open file…").clicked()
|
||||||
@@ -73,10 +73,10 @@ impl eframe::App for MyApp {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
preview_files_being_dropped(ctx);
|
preview_files_being_dropped(ui.ctx());
|
||||||
|
|
||||||
// Collect dropped files:
|
// Collect dropped files:
|
||||||
ctx.input(|i| {
|
ui.input(|i| {
|
||||||
if !i.raw.dropped_files.is_empty() {
|
if !i.raw.dropped_files.is_empty() {
|
||||||
self.dropped_files.clone_from(&i.raw.dropped_files);
|
self.dropped_files.clone_from(&i.raw.dropped_files);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -36,16 +36,16 @@ impl MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
// Reserve some space at the top so the demo ui isn't hidden behind the android status bar
|
// Reserve some space at the top so the demo ui isn't hidden behind the android status bar
|
||||||
// TODO(lucasmerlin): This is a pretty big hack, should be fixed once safe_area implemented
|
// TODO(lucasmerlin): This is a pretty big hack, should be fixed once safe_area implemented
|
||||||
// for android:
|
// for android:
|
||||||
// https://github.com/rust-windowing/winit/issues/3910
|
// https://github.com/rust-windowing/winit/issues/3910
|
||||||
egui::Panel::top("status_bar_space").show(ctx, |ui| {
|
egui::Panel::top("status_bar_space").show_inside(ui, |ui| {
|
||||||
ui.set_height(32.0);
|
ui.set_height(32.0);
|
||||||
});
|
});
|
||||||
|
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
self.demo.ui(ui);
|
self.demo.ui(ui);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -36,8 +36,8 @@ impl Default for MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("My egui Application");
|
ui.heading("My egui Application");
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
let name_label = ui.label("Your name: ");
|
let name_label = ui.label("Your name: ");
|
||||||
|
|||||||
@@ -116,15 +116,15 @@ impl std::ops::Drop for MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::Window::new("Main thread").show(ctx, |ui| {
|
egui::Window::new("Main thread").show(ui.ctx(), |ui| {
|
||||||
if ui.button("Spawn another thread").clicked() {
|
if ui.button("Spawn another thread").clicked() {
|
||||||
self.spawn_thread();
|
self.spawn_thread();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
for (_handle, show_tx) in &self.threads {
|
for (_handle, show_tx) in &self.threads {
|
||||||
let _ = show_tx.send(ctx.clone());
|
let _ = show_tx.send(ui.ctx().clone());
|
||||||
}
|
}
|
||||||
|
|
||||||
for _ in 0..self.threads.len() {
|
for _ in 0..self.threads.len() {
|
||||||
|
|||||||
@@ -15,8 +15,8 @@ fn main() -> eframe::Result {
|
|||||||
let mut name = "Arthur".to_owned();
|
let mut name = "Arthur".to_owned();
|
||||||
let mut age = 42;
|
let mut age = 42;
|
||||||
|
|
||||||
eframe::run_simple_native("My egui App", options, move |ctx, _frame| {
|
eframe::run_ui_native("My egui App", options, move |ui, _frame| {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("My egui Application");
|
ui.heading("My egui Application");
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
let name_label = ui.label("Your name: ");
|
let name_label = ui.label("Your name: ");
|
||||||
|
|||||||
@@ -24,8 +24,8 @@ fn main() -> eframe::Result {
|
|||||||
struct MyApp {}
|
struct MyApp {}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
egui::ScrollArea::both().show(ui, |ui| {
|
egui::ScrollArea::both().show(ui, |ui| {
|
||||||
ui.image(egui::include_image!("cat.webp"))
|
ui.image(egui::include_image!("cat.webp"))
|
||||||
.on_hover_text_at_pointer("WebP");
|
.on_hover_text_at_pointer("WebP");
|
||||||
|
|||||||
@@ -20,8 +20,8 @@ struct Content {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for Content {
|
impl eframe::App for Content {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("Press/Hold/Release example. Press A to test.");
|
ui.heading("Press/Hold/Release example. Press A to test.");
|
||||||
if ui.button("Clear").clicked() {
|
if ui.button("Clear").clicked() {
|
||||||
self.text.clear();
|
self.text.clear();
|
||||||
@@ -33,14 +33,14 @@ impl eframe::App for Content {
|
|||||||
ui.label(&self.text);
|
ui.label(&self.text);
|
||||||
});
|
});
|
||||||
|
|
||||||
if ctx.input(|i| i.key_pressed(Key::A)) {
|
if ui.input(|i| i.key_pressed(Key::A)) {
|
||||||
self.text.push_str("\nPressed");
|
self.text.push_str("\nPressed");
|
||||||
}
|
}
|
||||||
if ctx.input(|i| i.key_down(Key::A)) {
|
if ui.input(|i| i.key_down(Key::A)) {
|
||||||
self.text.push_str("\nHeld");
|
self.text.push_str("\nHeld");
|
||||||
ui.request_repaint(); // make sure we note the holding.
|
ui.request_repaint(); // make sure we note the holding.
|
||||||
}
|
}
|
||||||
if ctx.input(|i| i.key_released(Key::A)) {
|
if ui.input(|i| i.key_released(Key::A)) {
|
||||||
self.text.push_str("\nReleased");
|
self.text.push_str("\nReleased");
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -35,8 +35,8 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.label("Hello from the root viewport");
|
ui.label("Hello from the root viewport");
|
||||||
|
|
||||||
ui.checkbox(
|
ui.checkbox(
|
||||||
@@ -61,7 +61,7 @@ impl eframe::App for MyApp {
|
|||||||
});
|
});
|
||||||
|
|
||||||
if self.show_immediate_viewport {
|
if self.show_immediate_viewport {
|
||||||
ctx.show_viewport_immediate(
|
ui.ctx().show_viewport_immediate(
|
||||||
egui::ViewportId::from_hash_of("immediate_viewport"),
|
egui::ViewportId::from_hash_of("immediate_viewport"),
|
||||||
egui::ViewportBuilder::default()
|
egui::ViewportBuilder::default()
|
||||||
.with_title("Immediate Viewport")
|
.with_title("Immediate Viewport")
|
||||||
@@ -87,7 +87,7 @@ impl eframe::App for MyApp {
|
|||||||
|
|
||||||
if self.show_deferred_viewport.load(Ordering::Relaxed) {
|
if self.show_deferred_viewport.load(Ordering::Relaxed) {
|
||||||
let show_deferred_viewport = self.show_deferred_viewport.clone();
|
let show_deferred_viewport = self.show_deferred_viewport.clone();
|
||||||
ctx.show_viewport_deferred(
|
ui.ctx().show_viewport_deferred(
|
||||||
egui::ViewportId::from_hash_of("deferred_viewport"),
|
egui::ViewportId::from_hash_of("deferred_viewport"),
|
||||||
egui::ViewportBuilder::default()
|
egui::ViewportBuilder::default()
|
||||||
.with_title("Deferred Viewport")
|
.with_title("Deferred Viewport")
|
||||||
|
|||||||
@@ -18,8 +18,8 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &eframe::egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut eframe::egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
CentralPanel::default().show(ctx, |ui| {
|
CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.label("PopupCloseBehavior::CloseOnClick popup");
|
ui.label("PopupCloseBehavior::CloseOnClick popup");
|
||||||
ComboBox::from_label("ComboBox")
|
ComboBox::from_label("ComboBox")
|
||||||
.selected_text(format!("{}", self.number))
|
.selected_text(format!("{}", self.number))
|
||||||
|
|||||||
@@ -54,8 +54,8 @@ impl Default for MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("Example of how to use the puffin profiler with egui");
|
ui.heading("Example of how to use the puffin profiler with egui");
|
||||||
ui.separator();
|
ui.separator();
|
||||||
|
|
||||||
@@ -103,7 +103,7 @@ impl eframe::App for MyApp {
|
|||||||
});
|
});
|
||||||
|
|
||||||
if self.show_immediate_viewport {
|
if self.show_immediate_viewport {
|
||||||
ctx.show_viewport_immediate(
|
ui.ctx().show_viewport_immediate(
|
||||||
egui::ViewportId::from_hash_of("immediate_viewport"),
|
egui::ViewportId::from_hash_of("immediate_viewport"),
|
||||||
egui::ViewportBuilder::default()
|
egui::ViewportBuilder::default()
|
||||||
.with_title("Immediate Viewport")
|
.with_title("Immediate Viewport")
|
||||||
@@ -130,7 +130,7 @@ impl eframe::App for MyApp {
|
|||||||
|
|
||||||
if self.show_deferred_viewport.load(Ordering::Relaxed) {
|
if self.show_deferred_viewport.load(Ordering::Relaxed) {
|
||||||
let show_deferred_viewport = self.show_deferred_viewport.clone();
|
let show_deferred_viewport = self.show_deferred_viewport.clone();
|
||||||
ctx.show_viewport_deferred(
|
ui.ctx().show_viewport_deferred(
|
||||||
egui::ViewportId::from_hash_of("deferred_viewport"),
|
egui::ViewportId::from_hash_of("deferred_viewport"),
|
||||||
egui::ViewportBuilder::default()
|
egui::ViewportBuilder::default()
|
||||||
.with_title("Deferred Viewport")
|
.with_title("Deferred Viewport")
|
||||||
|
|||||||
@@ -27,8 +27,8 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
if let Some(screenshot) = self.screenshot.take() {
|
if let Some(screenshot) = self.screenshot.take() {
|
||||||
self.texture = Some(ui.ctx().load_texture(
|
self.texture = Some(ui.ctx().load_texture(
|
||||||
"screenshot",
|
"screenshot",
|
||||||
@@ -45,7 +45,7 @@ impl eframe::App for MyApp {
|
|||||||
|
|
||||||
if ui.button("save to 'top_left.png'").clicked() {
|
if ui.button("save to 'top_left.png'").clicked() {
|
||||||
self.save_to_file = true;
|
self.save_to_file = true;
|
||||||
ctx.send_viewport_cmd(egui::ViewportCommand::Screenshot(Default::default()));
|
ui.send_viewport_cmd(egui::ViewportCommand::Screenshot(Default::default()));
|
||||||
}
|
}
|
||||||
|
|
||||||
ui.with_layout(egui::Layout::top_down(egui::Align::RIGHT), |ui| {
|
ui.with_layout(egui::Layout::top_down(egui::Align::RIGHT), |ui| {
|
||||||
@@ -54,17 +54,13 @@ impl eframe::App for MyApp {
|
|||||||
.add(egui::Label::new("hover me!").sense(egui::Sense::hover()))
|
.add(egui::Label::new("hover me!").sense(egui::Sense::hover()))
|
||||||
.hovered()
|
.hovered()
|
||||||
{
|
{
|
||||||
ctx.set_theme(egui::Theme::Dark);
|
ui.ctx().set_theme(egui::Theme::Dark);
|
||||||
} else {
|
} else {
|
||||||
ctx.set_theme(egui::Theme::Light);
|
ui.ctx().set_theme(egui::Theme::Light);
|
||||||
}
|
}
|
||||||
ctx.send_viewport_cmd(
|
ui.send_viewport_cmd(egui::ViewportCommand::Screenshot(Default::default()));
|
||||||
egui::ViewportCommand::Screenshot(Default::default()),
|
|
||||||
);
|
|
||||||
} else if ui.button("take screenshot!").clicked() {
|
} else if ui.button("take screenshot!").clicked() {
|
||||||
ctx.send_viewport_cmd(
|
ui.send_viewport_cmd(egui::ViewportCommand::Screenshot(Default::default()));
|
||||||
egui::ViewportCommand::Screenshot(Default::default()),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -101,7 +97,7 @@ impl eframe::App for MyApp {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
ctx.request_repaint();
|
ui.request_repaint();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -43,8 +43,8 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
let label_text = if self.has_next {
|
let label_text = if self.has_next {
|
||||||
"When this window is closed the next will be opened after a short delay"
|
"When this window is closed the next will be opened after a short delay"
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
#![allow(rustdoc::missing_crate_level_docs)] // it's an example
|
#![allow(rustdoc::missing_crate_level_docs)] // it's an example
|
||||||
|
|
||||||
use eframe::{CreationContext, NativeOptions, egui};
|
use eframe::{CreationContext, NativeOptions, egui};
|
||||||
use egui::{Button, CentralPanel, Context, UserAttentionType};
|
use egui::{Button, CentralPanel, UserAttentionType};
|
||||||
|
|
||||||
use std::time::{Duration, SystemTime};
|
use std::time::{Duration, SystemTime};
|
||||||
|
|
||||||
@@ -55,12 +55,12 @@ impl Application {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for Application {
|
impl eframe::App for Application {
|
||||||
fn update(&mut self, ctx: &Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
if let Some(request_at) = self.request_at
|
if let Some(request_at) = self.request_at
|
||||||
&& request_at < SystemTime::now()
|
&& request_at < SystemTime::now()
|
||||||
{
|
{
|
||||||
self.request_at = None;
|
self.request_at = None;
|
||||||
ctx.send_viewport_cmd(egui::ViewportCommand::RequestUserAttention(self.attention));
|
ui.send_viewport_cmd(egui::ViewportCommand::RequestUserAttention(self.attention));
|
||||||
if self.auto_reset {
|
if self.auto_reset {
|
||||||
self.auto_reset = false;
|
self.auto_reset = false;
|
||||||
self.reset_at = Some(SystemTime::now() + Self::attention_reset_timeout());
|
self.reset_at = Some(SystemTime::now() + Self::attention_reset_timeout());
|
||||||
@@ -71,12 +71,12 @@ impl eframe::App for Application {
|
|||||||
&& reset_at < SystemTime::now()
|
&& reset_at < SystemTime::now()
|
||||||
{
|
{
|
||||||
self.reset_at = None;
|
self.reset_at = None;
|
||||||
ctx.send_viewport_cmd(egui::ViewportCommand::RequestUserAttention(
|
ui.send_viewport_cmd(egui::ViewportCommand::RequestUserAttention(
|
||||||
UserAttentionType::Reset,
|
UserAttentionType::Reset,
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
CentralPanel::default().show(ctx, |ui| {
|
CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.vertical(|ui| {
|
ui.vertical(|ui| {
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
ui.label("Attention type:");
|
ui.label("Attention type:");
|
||||||
@@ -131,6 +131,6 @@ impl eframe::App for Application {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
ctx.request_repaint_after(Self::repaint_max_timeout());
|
ui.request_repaint_after(Self::repaint_max_timeout());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -25,7 +25,7 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|||||||
struct MyTestApp {}
|
struct MyTestApp {}
|
||||||
|
|
||||||
impl eframe::App for MyTestApp {
|
impl eframe::App for MyTestApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, frame: &mut eframe::Frame) {
|
||||||
use glow::HasContext as _;
|
use glow::HasContext as _;
|
||||||
let gl = frame.gl().unwrap();
|
let gl = frame.gl().unwrap();
|
||||||
|
|
||||||
@@ -37,7 +37,7 @@ impl eframe::App for MyTestApp {
|
|||||||
gl.clear(glow::COLOR_BUFFER_BIT);
|
gl.clear(glow::COLOR_BUFFER_BIT);
|
||||||
}
|
}
|
||||||
|
|
||||||
egui::Window::new("Floating Window").show(ctx, |ui| {
|
egui::Window::new("Floating Window").show(ui.ctx(), |ui| {
|
||||||
ui.label("The background should be purple.");
|
ui.label("The background should be purple.");
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,9 +7,9 @@ fn main() -> eframe::Result {
|
|||||||
env_logger::init(); // Use `RUST_LOG=debug` to see logs.
|
env_logger::init(); // Use `RUST_LOG=debug` to see logs.
|
||||||
|
|
||||||
let options = eframe::NativeOptions::default();
|
let options = eframe::NativeOptions::default();
|
||||||
eframe::run_simple_native("My egui App", options, move |ctx, _frame| {
|
eframe::run_ui_native("My egui App", options, move |ui, _frame| {
|
||||||
// A bottom panel to force the tooltips to consider if the fit below or under the widget:
|
// A bottom panel to force the tooltips to consider if the fit below or under the widget:
|
||||||
egui::Panel::bottom("bottom").show(ctx, |ui| {
|
egui::Panel::bottom("bottom").show_inside(ui, |ui| {
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
ui.vertical(|ui| {
|
ui.vertical(|ui| {
|
||||||
ui.label("Single tooltips:");
|
ui.label("Single tooltips:");
|
||||||
@@ -33,10 +33,10 @@ fn main() -> eframe::Result {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.horizontal(|ui| {
|
ui.horizontal(|ui| {
|
||||||
if ui.button("Reset egui memory").clicked() {
|
if ui.button("Reset egui memory").clicked() {
|
||||||
ctx.memory_mut(|mem| *mem = Default::default());
|
ui.memory_mut(|mem| *mem = Default::default());
|
||||||
}
|
}
|
||||||
|
|
||||||
ui.with_layout(egui::Layout::right_to_left(egui::Align::BOTTOM), |ui| {
|
ui.with_layout(egui::Layout::right_to_left(egui::Align::BOTTOM), |ui| {
|
||||||
|
|||||||
@@ -31,10 +31,10 @@ struct MyApp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for MyApp {
|
impl eframe::App for MyApp {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
ctx.all_styles_mut(|style| style.interaction.tooltip_delay = 0.0);
|
ui.all_styles_mut(|style| style.interaction.tooltip_delay = 0.0);
|
||||||
|
|
||||||
egui::Panel::left("side_panel_left").show(ctx, |ui| {
|
egui::Panel::left("side_panel_left").show_inside(ui, |ui| {
|
||||||
ui.heading("Information");
|
ui.heading("Information");
|
||||||
ui.label(
|
ui.label(
|
||||||
"This is a demo/test environment of the `UiStack` feature. The tables display \
|
"This is a demo/test environment of the `UiStack` feature. The tables display \
|
||||||
@@ -49,7 +49,7 @@ impl eframe::App for MyApp {
|
|||||||
ui.checkbox(&mut self.show_memory, "📝 Memory");
|
ui.checkbox(&mut self.show_memory, "📝 Memory");
|
||||||
ui.add_space(10.0);
|
ui.add_space(10.0);
|
||||||
if ui.button("Reset egui memory").clicked() {
|
if ui.button("Reset egui memory").clicked() {
|
||||||
ctx.memory_mut(|mem| *mem = Default::default());
|
ui.memory_mut(|mem| *mem = Default::default());
|
||||||
}
|
}
|
||||||
ui.add_space(20.0);
|
ui.add_space(20.0);
|
||||||
|
|
||||||
@@ -82,7 +82,7 @@ impl eframe::App for MyApp {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
egui::Panel::right("side_panel_right").show(ctx, |ui| {
|
egui::Panel::right("side_panel_right").show_inside(ui, |ui| {
|
||||||
egui::ScrollArea::both().auto_shrink(false).show(ui, |ui| {
|
egui::ScrollArea::both().auto_shrink(false).show(ui, |ui| {
|
||||||
stack_ui(ui);
|
stack_ui(ui);
|
||||||
|
|
||||||
@@ -92,7 +92,7 @@ impl eframe::App for MyApp {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
egui::ScrollArea::both().auto_shrink(false).show(ui, |ui| {
|
egui::ScrollArea::both().auto_shrink(false).show(ui, |ui| {
|
||||||
ui.label("stack here:");
|
ui.label("stack here:");
|
||||||
stack_ui(ui);
|
stack_ui(ui);
|
||||||
@@ -172,7 +172,7 @@ impl eframe::App for MyApp {
|
|||||||
|
|
||||||
egui::Panel::bottom("bottom_panel")
|
egui::Panel::bottom("bottom_panel")
|
||||||
.resizable(true)
|
.resizable(true)
|
||||||
.show(ctx, |ui| {
|
.show_inside(ui, |ui| {
|
||||||
egui::ScrollArea::vertical()
|
egui::ScrollArea::vertical()
|
||||||
.auto_shrink(false)
|
.auto_shrink(false)
|
||||||
.show(ui, |ui| {
|
.show(ui, |ui| {
|
||||||
@@ -186,30 +186,31 @@ impl eframe::App for MyApp {
|
|||||||
|
|
||||||
egui::Window::new("Window")
|
egui::Window::new("Window")
|
||||||
.pivot(egui::Align2::RIGHT_TOP)
|
.pivot(egui::Align2::RIGHT_TOP)
|
||||||
.show(ctx, |ui| {
|
.show(ui.ctx(), |ui| {
|
||||||
full_span_widget(ui, false);
|
full_span_widget(ui, false);
|
||||||
ui.add_space(20.0);
|
ui.add_space(20.0);
|
||||||
stack_ui(ui);
|
stack_ui(ui);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
let ctx = ui.ctx().clone();
|
||||||
egui::Window::new("🔧 Settings")
|
egui::Window::new("🔧 Settings")
|
||||||
.open(&mut self.show_settings)
|
.open(&mut self.show_settings)
|
||||||
.vscroll(true)
|
.vscroll(true)
|
||||||
.show(ctx, |ui| {
|
.show(&ctx, |ui| {
|
||||||
ctx.settings_ui(ui);
|
ctx.settings_ui(ui);
|
||||||
});
|
});
|
||||||
|
|
||||||
egui::Window::new("🔍 Inspection")
|
egui::Window::new("🔍 Inspection")
|
||||||
.open(&mut self.show_inspection)
|
.open(&mut self.show_inspection)
|
||||||
.vscroll(true)
|
.vscroll(true)
|
||||||
.show(ctx, |ui| {
|
.show(&ctx, |ui| {
|
||||||
ctx.inspection_ui(ui);
|
ctx.inspection_ui(ui);
|
||||||
});
|
});
|
||||||
|
|
||||||
egui::Window::new("📝 Memory")
|
egui::Window::new("📝 Memory")
|
||||||
.open(&mut self.show_memory)
|
.open(&mut self.show_memory)
|
||||||
.resizable(false)
|
.resizable(false)
|
||||||
.show(ctx, |ui| {
|
.show(&ctx, |ui| {
|
||||||
ctx.memory_ui(ui);
|
ctx.memory_ui(ui);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -153,18 +153,18 @@ impl Default for App {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl eframe::App for App {
|
impl eframe::App for App {
|
||||||
fn update(&mut self, ctx: &egui::Context, _frame: &mut eframe::Frame) {
|
fn ui(&mut self, ui: &mut egui::Ui, _frame: &mut eframe::Frame) {
|
||||||
egui::CentralPanel::default().show(ctx, |ui| {
|
egui::CentralPanel::default().show_inside(ui, |ui| {
|
||||||
ui.heading("Root viewport");
|
ui.heading("Root viewport");
|
||||||
{
|
{
|
||||||
let mut embed_viewports = ctx.embed_viewports();
|
let mut embed_viewports = ui.embed_viewports();
|
||||||
ui.checkbox(&mut embed_viewports, "Embed all viewports");
|
ui.checkbox(&mut embed_viewports, "Embed all viewports");
|
||||||
if ui.button("Open all viewports").clicked() {
|
if ui.button("Open all viewports").clicked() {
|
||||||
for viewport in &self.top {
|
for viewport in &self.top {
|
||||||
viewport.write().set_visible_recursive(true);
|
viewport.write().set_visible_recursive(true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ctx.set_embed_viewports(embed_viewports);
|
ui.set_embed_viewports(embed_viewports);
|
||||||
}
|
}
|
||||||
ui.checkbox(&mut self.close_button, "with close button");
|
ui.checkbox(&mut self.close_button, "with close button");
|
||||||
generic_ui(ui, &self.top, self.close_button);
|
generic_ui(ui, &self.top, self.close_button);
|
||||||
|
|||||||
Reference in New Issue
Block a user