diff --git a/demo/common/src/ui.rs b/demo/common/src/ui.rs index 219723d6..56a94ad0 100644 --- a/demo/common/src/ui.rs +++ b/demo/common/src/ui.rs @@ -28,11 +28,6 @@ const SLIDER_KNOB_HEIGHT: i32 = 48; const EFFECTS_PANEL_WIDTH: i32 = 550; const EFFECTS_PANEL_HEIGHT: i32 = BUTTON_HEIGHT * 3 + PADDING * 4; -const OPEN_BUTTON_X: i32 = PADDING + (BUTTON_WIDTH + PADDING) * 1; -const SCREENSHOT_BUTTON_X: i32 = PADDING + (BUTTON_WIDTH + PADDING) * 2; -const THREE_D_SWITCH_X: i32 = PADDING + (BUTTON_WIDTH + PADDING) * 3; -const BACKGROUND_SWITCH_X: i32 = PADDING + (BUTTON_WIDTH + PADDING) * 3 + PADDING + SWITCH_SIZE; - const ROTATE_PANEL_X: i32 = PADDING + (BUTTON_WIDTH + PADDING) * 3 + (PADDING + SWITCH_SIZE) * 2; const ROTATE_PANEL_WIDTH: i32 = SLIDER_WIDTH + PADDING * 2; const ROTATE_PANEL_HEIGHT: i32 = PADDING * 2 + SLIDER_HEIGHT; @@ -110,79 +105,64 @@ impl DemoUI where D: Device { event: &mut UIEvent, action: &mut UIAction) { let bottom = debug_ui.ui.framebuffer_size().y() - PADDING; + let mut position = Point2DI32::new(PADDING, bottom - BUTTON_HEIGHT); // Draw effects button. - let effects_button_position = Point2DI32::new(PADDING, bottom - BUTTON_HEIGHT); - if debug_ui.ui.draw_button(device, event, effects_button_position, &self.effects_texture) { + if debug_ui.ui.draw_button(device, event, position, &self.effects_texture) { self.effects_panel_visible = !self.effects_panel_visible; } + position += Point2DI32::new(BUTTON_WIDTH + PADDING, 0); // Draw open button. - let lower_button_y = bottom - BUTTON_HEIGHT; - let open_button_position = Point2DI32::new(OPEN_BUTTON_X, lower_button_y); - if debug_ui.ui.draw_button(device, event, open_button_position, &self.open_texture) { + if debug_ui.ui.draw_button(device, event, position, &self.open_texture) { if let Ok(Response::Okay(file)) = nfd::open_file_dialog(Some("svg"), None) { *action = UIAction::OpenFile(PathBuf::from(file)); } } + position += Point2DI32::new(BUTTON_WIDTH + PADDING, 0); // Draw screenshot button. - let screenshot_button_position = Point2DI32::new(SCREENSHOT_BUTTON_X, lower_button_y); - if debug_ui.ui.draw_button(device, - event, - screenshot_button_position, - &self.screenshot_texture) { + if debug_ui.ui.draw_button(device, event, position, &self.screenshot_texture) { if let Ok(Response::Okay(file)) = nfd::open_save_dialog(Some("png"), None) { *action = UIAction::TakeScreenshot(PathBuf::from(file)); } } + position += Point2DI32::new(BUTTON_WIDTH + PADDING, 0); // Draw 3D switch. - let three_d_switch_origin = Point2DI32::new(THREE_D_SWITCH_X, lower_button_y); self.three_d_enabled = debug_ui.ui.draw_text_switch(device, event, - three_d_switch_origin, + position, "2D", "3D", self.three_d_enabled); + position += Point2DI32::new(SWITCH_SIZE + PADDING, 0); // Draw background switch. - let background_switch_origin = Point2DI32::new(BACKGROUND_SWITCH_X, lower_button_y); self.dark_background_enabled = debug_ui.ui.draw_image_switch(device, event, - background_switch_origin, + position, &self.bg_light_texture, &self.bg_dark_texture, self.dark_background_enabled); + position += Point2DI32::new(SWITCH_SIZE + PADDING, 0); // Draw rotate and zoom buttons, if applicable. if !self.three_d_enabled { - let rotate_button_y = bottom - BUTTON_HEIGHT; - let rotate_button_position = Point2DI32::new(ROTATE_PANEL_X, rotate_button_y); - if debug_ui.ui.draw_button(device, - event, - rotate_button_position, - &self.rotate_texture) { + if debug_ui.ui.draw_button(device, event, position, &self.rotate_texture) { self.rotate_panel_visible = !self.rotate_panel_visible; } + position += Point2DI32::new(BUTTON_WIDTH + PADDING, 0); - let zoom_in_button_x = ROTATE_PANEL_X + BUTTON_WIDTH + PADDING; - let zoom_in_button_position = Point2DI32::new(zoom_in_button_x, rotate_button_y); - if debug_ui.ui.draw_button(device, - event, - zoom_in_button_position, - &self.zoom_in_texture) { + if debug_ui.ui.draw_button(device, event, position, &self.zoom_in_texture) { *action = UIAction::ZoomIn; } + position += Point2DI32::new(BUTTON_WIDTH + PADDING, 0); - let zoom_out_button_x = ROTATE_PANEL_X + (BUTTON_WIDTH + PADDING) * 2; - let zoom_out_button_position = Point2DI32::new(zoom_out_button_x, rotate_button_y); - if debug_ui.ui.draw_button(device, - event, - zoom_out_button_position, - &self.zoom_out_texture) { + if debug_ui.ui.draw_button(device, event, position, &self.zoom_out_texture) { *action = UIAction::ZoomOut; } + position += Point2DI32::new(BUTTON_WIDTH + PADDING, 0); } // Draw effects panel, if necessary. diff --git a/geometry/src/basic/point.rs b/geometry/src/basic/point.rs index f42746d9..4ce494e8 100644 --- a/geometry/src/basic/point.rs +++ b/geometry/src/basic/point.rs @@ -229,6 +229,13 @@ impl Add for Point2DI32 { } } +impl AddAssign for Point2DI32 { + #[inline] + fn add_assign(&mut self, other: Point2DI32) { + self.0 += other.0 + } +} + impl Sub for Point2DI32 { type Output = Point2DI32; #[inline] diff --git a/renderer/src/gpu/debug.rs b/renderer/src/gpu/debug.rs index 6ef183ba..2c957624 100644 --- a/renderer/src/gpu/debug.rs +++ b/renderer/src/gpu/debug.rs @@ -19,7 +19,7 @@ use crate::gpu_data::Stats; use pathfinder_geometry::basic::point::Point2DI32; use pathfinder_geometry::basic::rect::RectI32; use pathfinder_gpu::{Device, Resources}; -use pathfinder_ui::{PADDING, UI, WINDOW_COLOR}; +use pathfinder_ui::{FONT_ASCENT, LINE_HEIGHT, PADDING, UI, WINDOW_COLOR}; use std::collections::VecDeque; use std::ops::{Add, Div}; use std::time::Duration; @@ -28,8 +28,6 @@ const SAMPLE_BUFFER_SIZE: usize = 60; const PERF_WINDOW_WIDTH: i32 = 375; const PERF_WINDOW_HEIGHT: i32 = LINE_HEIGHT * 6 + PADDING + 2; -const FONT_ASCENT: i32 = 28; -const LINE_HEIGHT: i32 = 42; pub struct DebugUI where D: Device { pub ui: UI, @@ -93,6 +91,8 @@ impl DebugUI where D: Device { &format!("GPU Time: {:.3} ms", duration_to_ms(mean_gpu_sample.elapsed)), origin + Point2DI32::new(0, LINE_HEIGHT * 5), false); + + self.ui.draw_tooltip(device, "Hello world", Point2DI32::default()); } } diff --git a/simd/src/extras.rs b/simd/src/extras.rs index 51442c37..8abea386 100644 --- a/simd/src/extras.rs +++ b/simd/src/extras.rs @@ -8,7 +8,10 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use crate::default::F32x4; +use crate::default::{F32x4, I32x4}; +use std::ops::{AddAssign, MulAssign, Neg, SubAssign}; + +// 32-bit floats impl F32x4 { // Constructors @@ -72,3 +75,63 @@ impl F32x4 { .is_all_zeroes() } } + +impl AddAssign for F32x4 { + #[inline] + fn add_assign(&mut self, other: F32x4) { + *self = *self + other + } +} + +impl SubAssign for F32x4 { + #[inline] + fn sub_assign(&mut self, other: F32x4) { + *self = *self - other + } +} + +impl MulAssign for F32x4 { + #[inline] + fn mul_assign(&mut self, other: F32x4) { + *self = *self * other + } +} + +impl Neg for F32x4 { + type Output = F32x4; + #[inline] + fn neg(self) -> F32x4 { + F32x4::default() - self + } +} + +// 32-bit integers + +impl AddAssign for I32x4 { + #[inline] + fn add_assign(&mut self, other: I32x4) { + *self = *self + other + } +} + +impl SubAssign for I32x4 { + #[inline] + fn sub_assign(&mut self, other: I32x4) { + *self = *self - other + } +} + +impl MulAssign for I32x4 { + #[inline] + fn mul_assign(&mut self, other: I32x4) { + *self = *self * other + } +} + +impl Neg for I32x4 { + type Output = I32x4; + #[inline] + fn neg(self) -> I32x4 { + I32x4::default() - self + } +} diff --git a/simd/src/x86.rs b/simd/src/x86.rs index bedb5a1d..f3d07a72 100644 --- a/simd/src/x86.rs +++ b/simd/src/x86.rs @@ -12,7 +12,7 @@ use std::arch::x86_64::{self, __m128, __m128i}; use std::cmp::PartialEq; use std::fmt::{self, Debug, Formatter}; use std::mem; -use std::ops::{Add, AddAssign, BitXor, Index, IndexMut, Mul, MulAssign, Neg, Not, Sub, SubAssign}; +use std::ops::{Add, BitXor, Index, IndexMut, Mul, Not, Sub}; // 32-bit floats @@ -1478,13 +1478,6 @@ impl Add for F32x4 { } } -impl AddAssign for F32x4 { - #[inline] - fn add_assign(&mut self, other: F32x4) { - unsafe { self.0 = x86_64::_mm_add_ps(self.0, other.0) } - } -} - impl Mul for F32x4 { type Output = F32x4; #[inline] @@ -1493,13 +1486,6 @@ impl Mul for F32x4 { } } -impl MulAssign for F32x4 { - #[inline] - fn mul_assign(&mut self, other: F32x4) { - unsafe { self.0 = x86_64::_mm_mul_ps(self.0, other.0) } - } -} - impl Sub for F32x4 { type Output = F32x4; #[inline] @@ -1508,21 +1494,6 @@ impl Sub for F32x4 { } } -impl SubAssign for F32x4 { - #[inline] - fn sub_assign(&mut self, other: F32x4) { - unsafe { self.0 = x86_64::_mm_sub_ps(self.0, other.0) } - } -} - -impl Neg for F32x4 { - type Output = F32x4; - #[inline] - fn neg(self) -> F32x4 { - F32x4::default() - self - } -} - // 32-bit signed integers #[derive(Clone, Copy)] diff --git a/ui/src/lib.rs b/ui/src/lib.rs index 4a47eb4e..4402d9b2 100644 --- a/ui/src/lib.rs +++ b/ui/src/lib.rs @@ -29,12 +29,17 @@ use std::io::BufReader; pub const PADDING: i32 = 12; +pub const LINE_HEIGHT: i32 = 42; +pub const FONT_ASCENT: i32 = 28; + pub const BUTTON_WIDTH: i32 = PADDING * 2 + ICON_SIZE; pub const BUTTON_HEIGHT: i32 = PADDING * 2 + ICON_SIZE; pub const BUTTON_TEXT_OFFSET: i32 = PADDING + 36; pub const SWITCH_SIZE: i32 = SWITCH_HALF_SIZE * 2 + 1; +pub const TOOLTIP_HEIGHT: i32 = FONT_ASCENT + PADDING * 2; + const DEBUG_TEXTURE_VERTEX_SIZE: usize = 8; const DEBUG_SOLID_VERTEX_SIZE: usize = 4; @@ -513,6 +518,16 @@ impl UI where D: Device { value } + + pub fn draw_tooltip(&self, device: &D, string: &str, origin: Point2DI32) { + let text_size = self.measure_text(string); + let window_size = Point2DI32::new(text_size + PADDING * 2, TOOLTIP_HEIGHT); + self.draw_solid_rounded_rect(device, RectI32::new(origin, window_size), WINDOW_COLOR); + self.draw_text(device, + string, + origin + Point2DI32::new(PADDING, PADDING + FONT_ASCENT), + false); + } } struct DebugTextureProgram where D: Device {