[egui_web] respect the native zoom/scale of the browser

Remove all complexity with own scale slider.

Closes https://github.com/emilk/egui/issues/53
This commit is contained in:
Emil Ernerfeldt 2020-11-28 10:46:31 +01:00
parent b1b34de4ee
commit 8de74e4250
3 changed files with 22 additions and 37 deletions

View file

@ -209,10 +209,12 @@ impl DemoApp {
self.frame_history.ui(ui); self.frame_history.ui(ui);
ui.separator(); if !is_web {
// web browsers have their own way of zooming, which egui_web respects
integration_context.output.pixels_per_point = ui.separator();
self.pixels_per_point_ui(ui, &integration_context.info); integration_context.output.pixels_per_point =
self.pixels_per_point_ui(ui, &integration_context.info);
}
if !is_web { if !is_web {
ui.separator(); ui.separator();

View file

@ -102,30 +102,19 @@ impl egui::app::TextureAllocator for webgl::Painter {
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
/// Data gathered between frames. /// Data gathered between frames.
/// Is translated to `egui::RawInput` at the start of each frame.
#[derive(Default)] #[derive(Default)]
pub struct WebInput { pub struct WebInput {
/// In native points (not same as Egui points)
pub mouse_pos: Option<egui::Pos2>,
/// Is this a touch screen? If so, we ignore mouse events. /// Is this a touch screen? If so, we ignore mouse events.
pub is_touch: bool, pub is_touch: bool,
/// In native points (not same as Egui points)
pub scroll_delta: egui::Vec2,
pub raw: egui::RawInput, pub raw: egui::RawInput,
} }
impl WebInput { impl WebInput {
pub fn new_frame(&mut self, pixels_per_point: f32) -> egui::RawInput { pub fn new_frame(&mut self) -> egui::RawInput {
// Compensate for potential different scale of Egui compared to native.
let scale = native_pixels_per_point() / pixels_per_point;
let scroll_delta = std::mem::take(&mut self.scroll_delta) * scale;
let mouse_pos = self.mouse_pos.map(|mp| pos2(mp.x * scale, mp.y * scale));
egui::RawInput { egui::RawInput {
mouse_pos, screen_size: screen_size_in_native_points().unwrap(),
scroll_delta, pixels_per_point: Some(native_pixels_per_point()),
screen_size: screen_size_in_native_points().unwrap() * scale,
pixels_per_point: Some(pixels_per_point),
time: now_sec(), time: now_sec(),
..self.raw.take() ..self.raw.take()
} }
@ -163,7 +152,6 @@ impl egui::app::RepaintSignal for NeedRepaint {
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
pub struct AppRunner { pub struct AppRunner {
pixels_per_point: f32,
pub web_backend: WebBackend, pub web_backend: WebBackend,
pub input: WebInput, pub input: WebInput,
pub app: Box<dyn App>, pub app: Box<dyn App>,
@ -174,7 +162,6 @@ impl AppRunner {
pub fn new(web_backend: WebBackend, mut app: Box<dyn App>) -> Result<Self, JsValue> { pub fn new(web_backend: WebBackend, mut app: Box<dyn App>) -> Result<Self, JsValue> {
app.setup(&web_backend.ctx); app.setup(&web_backend.ctx);
Ok(Self { Ok(Self {
pixels_per_point: native_pixels_per_point(),
web_backend, web_backend,
input: Default::default(), input: Default::default(),
app, app,
@ -189,7 +176,7 @@ impl AppRunner {
pub fn logic(&mut self) -> Result<(egui::Output, egui::PaintJobs), JsValue> { pub fn logic(&mut self) -> Result<(egui::Output, egui::PaintJobs), JsValue> {
resize_canvas_to_screen_size(self.web_backend.canvas_id()); resize_canvas_to_screen_size(self.web_backend.canvas_id());
let raw_input = self.input.new_frame(self.pixels_per_point); let raw_input = self.input.new_frame();
self.web_backend.begin_frame(raw_input); self.web_backend.begin_frame(raw_input);
let mut integration_context = egui::app::IntegrationContext { let mut integration_context = egui::app::IntegrationContext {
@ -214,14 +201,10 @@ impl AppRunner {
{ {
let egui::app::AppOutput { let egui::app::AppOutput {
quit: _, // Can't quit a web page quit: _, // Can't quit a web page
window_size: _, // Can't resize a web page window_size: _, // Can't resize a web page
pixels_per_point, pixels_per_point: _, // Can't zoom from within the app (we respect the web browser's zoom level)
} = app_output; } = app_output;
if let Some(pixels_per_point) = pixels_per_point {
self.pixels_per_point = pixels_per_point;
}
} }
Ok((egui_output, paint_jobs)) Ok((egui_output, paint_jobs))

View file

@ -498,7 +498,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
if !runner_lock.input.is_touch { if !runner_lock.input.is_touch {
runner_lock.input.mouse_pos = runner_lock.input.raw.mouse_pos =
Some(pos_from_mouse_event(runner_lock.canvas_id(), &event)); Some(pos_from_mouse_event(runner_lock.canvas_id(), &event));
runner_lock.input.raw.mouse_down = true; runner_lock.input.raw.mouse_down = true;
runner_lock.logic().unwrap(); // in case we get "mouseup" the same frame. TODO: handle via events instead runner_lock.logic().unwrap(); // in case we get "mouseup" the same frame. TODO: handle via events instead
@ -517,7 +517,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
if !runner_lock.input.is_touch { if !runner_lock.input.is_touch {
runner_lock.input.mouse_pos = runner_lock.input.raw.mouse_pos =
Some(pos_from_mouse_event(runner_lock.canvas_id(), &event)); Some(pos_from_mouse_event(runner_lock.canvas_id(), &event));
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
event.stop_propagation(); event.stop_propagation();
@ -534,7 +534,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
if !runner_lock.input.is_touch { if !runner_lock.input.is_touch {
runner_lock.input.mouse_pos = runner_lock.input.raw.mouse_pos =
Some(pos_from_mouse_event(runner_lock.canvas_id(), &event)); Some(pos_from_mouse_event(runner_lock.canvas_id(), &event));
runner_lock.input.raw.mouse_down = false; runner_lock.input.raw.mouse_down = false;
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
@ -552,7 +552,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::MouseEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
if !runner_lock.input.is_touch { if !runner_lock.input.is_touch {
runner_lock.input.mouse_pos = None; runner_lock.input.raw.mouse_pos = None;
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
event.stop_propagation(); event.stop_propagation();
event.prevent_default(); event.prevent_default();
@ -568,7 +568,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let closure = Closure::wrap(Box::new(move |event: web_sys::TouchEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::TouchEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
runner_lock.input.is_touch = true; runner_lock.input.is_touch = true;
runner_lock.input.mouse_pos = Some(pos_from_touch_event(&event)); runner_lock.input.raw.mouse_pos = Some(pos_from_touch_event(&event));
runner_lock.input.raw.mouse_down = true; runner_lock.input.raw.mouse_down = true;
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
event.stop_propagation(); event.stop_propagation();
@ -584,7 +584,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let closure = Closure::wrap(Box::new(move |event: web_sys::TouchEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::TouchEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
runner_lock.input.is_touch = true; runner_lock.input.is_touch = true;
runner_lock.input.mouse_pos = Some(pos_from_touch_event(&event)); runner_lock.input.raw.mouse_pos = Some(pos_from_touch_event(&event));
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
event.stop_propagation(); event.stop_propagation();
event.prevent_default(); event.prevent_default();
@ -601,7 +601,7 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
runner_lock.input.is_touch = true; runner_lock.input.is_touch = true;
runner_lock.input.raw.mouse_down = false; // First release mouse to click... runner_lock.input.raw.mouse_down = false; // First release mouse to click...
runner_lock.logic().unwrap(); // ...do the clicking... (TODO: handle via events instead) runner_lock.logic().unwrap(); // ...do the clicking... (TODO: handle via events instead)
runner_lock.input.mouse_pos = None; // ...remove hover effect runner_lock.input.raw.mouse_pos = None; // ...remove hover effect
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
event.stop_propagation(); event.stop_propagation();
event.prevent_default(); event.prevent_default();
@ -615,8 +615,8 @@ fn install_canvas_events(runner_ref: &AppRunnerRef) -> Result<(), JsValue> {
let runner_ref = runner_ref.clone(); let runner_ref = runner_ref.clone();
let closure = Closure::wrap(Box::new(move |event: web_sys::WheelEvent| { let closure = Closure::wrap(Box::new(move |event: web_sys::WheelEvent| {
let mut runner_lock = runner_ref.0.lock(); let mut runner_lock = runner_ref.0.lock();
runner_lock.input.scroll_delta.x -= event.delta_x() as f32; runner_lock.input.raw.scroll_delta.x -= event.delta_x() as f32;
runner_lock.input.scroll_delta.y -= event.delta_y() as f32; runner_lock.input.raw.scroll_delta.y -= event.delta_y() as f32;
runner_lock.needs_repaint.set_true(); runner_lock.needs_repaint.set_true();
event.stop_propagation(); event.stop_propagation();
event.prevent_default(); event.prevent_default();