mirror of
https://github.com/Zenithsiz/zsw.git
synced 2026-02-03 09:50:31 +00:00
Added a new display geometry type and moved all geometry uniform calculations to it.
This commit is contained in:
parent
ca8b98e106
commit
ddf753e466
@ -1,12 +1,16 @@
|
||||
//! Display
|
||||
|
||||
// Modules
|
||||
pub mod geometry;
|
||||
pub mod ser;
|
||||
|
||||
// Exports
|
||||
pub use self::geometry::DisplayGeometry;
|
||||
|
||||
// Imports
|
||||
use {
|
||||
std::{borrow::Borrow, fmt, sync::Arc},
|
||||
zsw_util::{Rect, ResourceManager, resource_manager},
|
||||
zsw_util::{ResourceManager, resource_manager},
|
||||
};
|
||||
|
||||
/// Displays
|
||||
@ -19,7 +23,7 @@ pub struct Display {
|
||||
pub name: DisplayName,
|
||||
|
||||
/// Geometries
|
||||
pub geometries: Vec<Rect<i32, u32>>,
|
||||
pub geometries: Vec<DisplayGeometry>,
|
||||
}
|
||||
|
||||
impl resource_manager::FromSerialized<DisplayName, ser::Display> for Display {
|
||||
@ -29,7 +33,7 @@ impl resource_manager::FromSerialized<DisplayName, ser::Display> for Display {
|
||||
geometries: display
|
||||
.geometries
|
||||
.into_iter()
|
||||
.map(|geometry| geometry.geometry)
|
||||
.map(|geometry| DisplayGeometry::new(geometry.geometry))
|
||||
.collect(),
|
||||
}
|
||||
}
|
||||
@ -41,7 +45,9 @@ impl resource_manager::ToSerialized<DisplayName, ser::Display> for Display {
|
||||
geometries: self
|
||||
.geometries
|
||||
.iter()
|
||||
.map(|&geometry| ser::DisplayGeometry { geometry })
|
||||
.map(|&geometry| ser::DisplayGeometry {
|
||||
geometry: geometry.into_inner(),
|
||||
})
|
||||
.collect(),
|
||||
}
|
||||
}
|
||||
|
||||
109
zsw/src/display/geometry.rs
Normal file
109
zsw/src/display/geometry.rs
Normal file
@ -0,0 +1,109 @@
|
||||
//! Display geometry
|
||||
|
||||
// Imports
|
||||
use {
|
||||
cgmath::{Matrix4, Vector2, Vector3},
|
||||
num_rational::Rational32,
|
||||
winit::dpi::PhysicalSize,
|
||||
zsw_util::Rect,
|
||||
};
|
||||
|
||||
#[derive(PartialEq, Eq, Clone, Copy, Debug)]
|
||||
pub struct DisplayGeometry {
|
||||
/// Inner geometry
|
||||
inner: Rect<i32, u32>,
|
||||
}
|
||||
|
||||
impl DisplayGeometry {
|
||||
/// Creates a new geometry
|
||||
pub fn new(inner: Rect<i32, u32>) -> Self {
|
||||
Self { inner }
|
||||
}
|
||||
|
||||
/// Unwraps this geometry into the inner rect
|
||||
pub(super) fn into_inner(self) -> Rect<i32, u32> {
|
||||
self.inner
|
||||
}
|
||||
|
||||
/// Gets the inner rectangle mutably
|
||||
pub fn as_rect_mut(&mut self) -> &mut Rect<i32, u32> {
|
||||
&mut self.inner
|
||||
}
|
||||
|
||||
/// Returns if this geometry intersects a window
|
||||
pub fn intersects_window(&self, window_geometry: Rect<i32, u32>) -> bool {
|
||||
self.inner.intersection(window_geometry).is_some()
|
||||
}
|
||||
|
||||
/// Returns this geometry's rectangle for a certain window
|
||||
pub fn on_window(&self, window_geometry: Rect<i32, u32>) -> Rect<i32, u32> {
|
||||
let mut geometry = self.inner;
|
||||
geometry.pos -= Vector2::new(window_geometry.pos.x, window_geometry.pos.y);
|
||||
|
||||
geometry
|
||||
}
|
||||
|
||||
/// Calculates this panel's position matrix
|
||||
// Note: This matrix simply goes from a geometry in physical units
|
||||
// onto shader coordinates.
|
||||
#[must_use]
|
||||
pub fn pos_matrix(&self, window_geometry: Rect<i32, u32>, surface_size: PhysicalSize<u32>) -> Matrix4<f32> {
|
||||
let geometry = self.on_window(window_geometry);
|
||||
|
||||
let x_scale = geometry.size[0] as f32 / surface_size.width as f32;
|
||||
let y_scale = geometry.size[1] as f32 / surface_size.height as f32;
|
||||
|
||||
let x_offset = geometry.pos[0] as f32 / surface_size.width as f32;
|
||||
let y_offset = geometry.pos[1] as f32 / surface_size.height as f32;
|
||||
|
||||
let translation = Matrix4::from_translation(Vector3::new(
|
||||
-1.0 + x_scale + 2.0 * x_offset,
|
||||
1.0 - y_scale - 2.0 * y_offset,
|
||||
0.0,
|
||||
));
|
||||
let scaling = Matrix4::from_nonuniform_scale(x_scale, -y_scale, 1.0);
|
||||
translation * scaling
|
||||
}
|
||||
|
||||
/// Calculates an image's ratio for this panel geometry
|
||||
///
|
||||
/// This ratio is multiplied by the base uvs to fix the stretching
|
||||
/// that comes from having a square coordinate system [0.0 .. 1.0] x [0.0 .. 1.0]
|
||||
pub fn image_ratio(&self, image_size: Vector2<u32>) -> Vector2<f32> {
|
||||
let image_size = image_size.cast().expect("Image size didn't fit into an `i32`");
|
||||
let panel_size = self.inner.size.cast().expect("Panel size didn't fit into an `i32`");
|
||||
|
||||
// If either the image or our panel have a side with 0, return a square ratio
|
||||
// TODO: Check if this is the right thing to do
|
||||
if panel_size.x == 0 || panel_size.y == 0 || image_size.x == 0 || image_size.y == 0 {
|
||||
return Vector2::new(0.0, 0.0);
|
||||
}
|
||||
|
||||
// Image and panel ratios
|
||||
let image_ratio = Rational32::new(image_size.x, image_size.y);
|
||||
let panel_ratio = Rational32::new(panel_size.x, panel_size.y);
|
||||
|
||||
// Ratios between the image and panel
|
||||
let width_ratio = Rational32::new(panel_size.x, image_size.x);
|
||||
let height_ratio = Rational32::new(panel_size.y, image_size.y);
|
||||
|
||||
// X-axis ratio, if image scrolls horizontally
|
||||
let x_ratio = self::ratio_as_f32(width_ratio / height_ratio);
|
||||
|
||||
// Y-axis ratio, if image scrolls vertically
|
||||
let y_ratio = self::ratio_as_f32(height_ratio / width_ratio);
|
||||
|
||||
match image_ratio >= panel_ratio {
|
||||
true => Vector2::new(x_ratio, 1.0),
|
||||
false => Vector2::new(1.0, y_ratio),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Converts a `Ratio<i32>` to `f32`, rounding
|
||||
// TODO: Although image and window sizes fit into an `f32`, maybe a
|
||||
// rational of the two wouldn't fit properly when in a num / denom
|
||||
// format, since both may be bigger than `2^24`, check if this is fine.
|
||||
fn ratio_as_f32(ratio: Rational32) -> f32 {
|
||||
*ratio.numer() as f32 / *ratio.denom() as f32
|
||||
}
|
||||
181
zsw/src/main.rs
181
zsw/src/main.rs
@ -46,7 +46,7 @@ use {
|
||||
display::Displays,
|
||||
menu::Menu,
|
||||
metrics::Metrics,
|
||||
panel::{PanelGeometry, Panels, PanelsRenderer, PanelsRendererShared},
|
||||
panel::{Panels, PanelsRenderer, PanelsRendererShared},
|
||||
playlist::Playlists,
|
||||
profile::{ProfileName, Profiles},
|
||||
shared::Shared,
|
||||
@ -376,96 +376,97 @@ async fn paint_egui(
|
||||
menu: &mut Menu,
|
||||
window_geometry: Rect<i32, u32>,
|
||||
) -> Result<(Vec<egui::ClippedPrimitive>, egui::TexturesDelta), AppError> {
|
||||
let full_output_fut =
|
||||
egui_painter.draw(window, async |ctx| {
|
||||
// Draw the menu
|
||||
tokio::task::block_in_place(|| {
|
||||
menu.draw(
|
||||
ctx,
|
||||
&shared.wgpu,
|
||||
&shared.displays,
|
||||
&shared.playlists,
|
||||
&shared.profiles,
|
||||
&shared.panels,
|
||||
&shared.metrics,
|
||||
&shared.window_monitor_names,
|
||||
&shared.event_loop_proxy,
|
||||
window_geometry,
|
||||
)
|
||||
});
|
||||
|
||||
|
||||
// Then go through all panels checking for interactions with their geometries
|
||||
// TODO: Should this be done here and not somewhere else?
|
||||
let Some(pointer_pos) = ctx.input(|input| input.pointer.latest_pos()) else {
|
||||
return Ok(());
|
||||
};
|
||||
let pointer_pos = Point2::new(pointer_pos.x as i32, pointer_pos.y as i32);
|
||||
shared
|
||||
.panels
|
||||
.for_each(async |panel| {
|
||||
let panel = &mut *panel.lock().await;
|
||||
let display = panel.display.read().await;
|
||||
|
||||
// If we're over an egui area, or none of the geometries are underneath the cursor, skip the panel
|
||||
if ctx.is_pointer_over_area() ||
|
||||
!display.geometries.iter().any(|&geometry| {
|
||||
PanelGeometry::geometry_on(geometry, window_geometry).contains(pointer_pos)
|
||||
}) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Pause any double-clicked panels
|
||||
if ctx.input(|input| input.pointer.button_double_clicked(egui::PointerButton::Primary)) {
|
||||
#[expect(clippy::match_same_arms, reason = "We'll be changing them soon")]
|
||||
match &mut panel.state {
|
||||
panel::PanelState::None(_) => (),
|
||||
panel::PanelState::Fade(state) => state.toggle_paused(),
|
||||
panel::PanelState::Slide(_) => (),
|
||||
}
|
||||
}
|
||||
|
||||
// Skip any ctrl-clicked/middle clicked panels
|
||||
if ctx.input(|input| {
|
||||
(input.pointer.button_clicked(egui::PointerButton::Primary) && input.modifiers.ctrl) ||
|
||||
input.pointer.button_clicked(egui::PointerButton::Middle)
|
||||
}) {
|
||||
#[expect(clippy::match_same_arms, reason = "We'll be changing them soon")]
|
||||
match &mut panel.state {
|
||||
panel::PanelState::None(_) => (),
|
||||
panel::PanelState::Fade(state) => state.skip(&shared.wgpu).await,
|
||||
panel::PanelState::Slide(_) => (),
|
||||
}
|
||||
}
|
||||
|
||||
// Scroll panels
|
||||
let scroll_delta = ctx.input(|input| input.smooth_scroll_delta.y);
|
||||
if scroll_delta != 0.0 {
|
||||
#[expect(clippy::match_same_arms, reason = "We'll be changing them soon")]
|
||||
match &mut panel.state {
|
||||
panel::PanelState::None(_) => (),
|
||||
panel::PanelState::Fade(state) => {
|
||||
// TODO: Make this "speed" configurable
|
||||
// TODO: Perform the conversion better without going through nanos
|
||||
let speed = 1.0 / 1000.0;
|
||||
let time_delta_abs = state.duration().mul_f32(scroll_delta.abs() * speed);
|
||||
let time_delta_abs =
|
||||
TimeDelta::from_std(time_delta_abs).expect("Offset didn't fit into time delta");
|
||||
let time_delta = match scroll_delta.is_sign_positive() {
|
||||
true => -time_delta_abs,
|
||||
false => time_delta_abs,
|
||||
};
|
||||
|
||||
state.step(&shared.wgpu, time_delta).await;
|
||||
},
|
||||
panel::PanelState::Slide(_) => (),
|
||||
}
|
||||
}
|
||||
})
|
||||
.await;
|
||||
|
||||
Ok::<_, !>(())
|
||||
let full_output_fut = egui_painter.draw(window, async |ctx| {
|
||||
// Draw the menu
|
||||
tokio::task::block_in_place(|| {
|
||||
menu.draw(
|
||||
ctx,
|
||||
&shared.wgpu,
|
||||
&shared.displays,
|
||||
&shared.playlists,
|
||||
&shared.profiles,
|
||||
&shared.panels,
|
||||
&shared.metrics,
|
||||
&shared.window_monitor_names,
|
||||
&shared.event_loop_proxy,
|
||||
window_geometry,
|
||||
)
|
||||
});
|
||||
|
||||
|
||||
// Then go through all panels checking for interactions with their geometries
|
||||
// TODO: Should this be done here and not somewhere else?
|
||||
let Some(pointer_pos) = ctx.input(|input| input.pointer.latest_pos()) else {
|
||||
return Ok(());
|
||||
};
|
||||
let pointer_pos = Point2::new(pointer_pos.x as i32, pointer_pos.y as i32);
|
||||
shared
|
||||
.panels
|
||||
.for_each(async |panel| {
|
||||
let panel = &mut *panel.lock().await;
|
||||
let display = panel.display.read().await;
|
||||
|
||||
// If we're over an egui area, or none of the geometries are underneath the cursor, skip the panel
|
||||
if ctx.is_pointer_over_area() ||
|
||||
!display
|
||||
.geometries
|
||||
.iter()
|
||||
.any(|&geometry| geometry.on_window(window_geometry).contains(pointer_pos))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// Pause any double-clicked panels
|
||||
if ctx.input(|input| input.pointer.button_double_clicked(egui::PointerButton::Primary)) {
|
||||
#[expect(clippy::match_same_arms, reason = "We'll be changing them soon")]
|
||||
match &mut panel.state {
|
||||
panel::PanelState::None(_) => (),
|
||||
panel::PanelState::Fade(state) => state.toggle_paused(),
|
||||
panel::PanelState::Slide(_) => (),
|
||||
}
|
||||
}
|
||||
|
||||
// Skip any ctrl-clicked/middle clicked panels
|
||||
if ctx.input(|input| {
|
||||
(input.pointer.button_clicked(egui::PointerButton::Primary) && input.modifiers.ctrl) ||
|
||||
input.pointer.button_clicked(egui::PointerButton::Middle)
|
||||
}) {
|
||||
#[expect(clippy::match_same_arms, reason = "We'll be changing them soon")]
|
||||
match &mut panel.state {
|
||||
panel::PanelState::None(_) => (),
|
||||
panel::PanelState::Fade(state) => state.skip(&shared.wgpu).await,
|
||||
panel::PanelState::Slide(_) => (),
|
||||
}
|
||||
}
|
||||
|
||||
// Scroll panels
|
||||
let scroll_delta = ctx.input(|input| input.smooth_scroll_delta.y);
|
||||
if scroll_delta != 0.0 {
|
||||
#[expect(clippy::match_same_arms, reason = "We'll be changing them soon")]
|
||||
match &mut panel.state {
|
||||
panel::PanelState::None(_) => (),
|
||||
panel::PanelState::Fade(state) => {
|
||||
// TODO: Make this "speed" configurable
|
||||
// TODO: Perform the conversion better without going through nanos
|
||||
let speed = 1.0 / 1000.0;
|
||||
let time_delta_abs = state.duration().mul_f32(scroll_delta.abs() * speed);
|
||||
let time_delta_abs =
|
||||
TimeDelta::from_std(time_delta_abs).expect("Offset didn't fit into time delta");
|
||||
let time_delta = match scroll_delta.is_sign_positive() {
|
||||
true => -time_delta_abs,
|
||||
false => time_delta_abs,
|
||||
};
|
||||
|
||||
state.step(&shared.wgpu, time_delta).await;
|
||||
},
|
||||
panel::PanelState::Slide(_) => (),
|
||||
}
|
||||
}
|
||||
})
|
||||
.await;
|
||||
|
||||
Ok::<_, !>(())
|
||||
});
|
||||
let full_output = full_output_fut.await?;
|
||||
let paint_jobs = egui_painter
|
||||
.tessellate_shapes(full_output.shapes, full_output.pixels_per_point)
|
||||
|
||||
@ -2,7 +2,7 @@
|
||||
|
||||
// Imports
|
||||
use {
|
||||
crate::display::{Display, DisplayName, Displays},
|
||||
crate::display::{Display, DisplayGeometry, DisplayName, Displays},
|
||||
std::sync::Arc,
|
||||
zsw_util::{Rect, TokioTaskBlockOn},
|
||||
zutil_cloned::cloned,
|
||||
@ -28,7 +28,7 @@ pub fn draw_displays_tab(ui: &mut egui::Ui, displays: &Arc<Displays>) {
|
||||
|
||||
ui.collapsing("New", |ui| {
|
||||
let name = super::get_data::<String>(ui, "display-tab-new-name");
|
||||
let geometries = super::get_data::<Vec<Rect<i32, u32>>>(ui, "display-tab-new-geometries");
|
||||
let geometries = super::get_data::<Vec<DisplayGeometry>>(ui, "display-tab-new-geometries");
|
||||
|
||||
ui.horizontal(|ui| {
|
||||
ui.label("Name");
|
||||
@ -58,13 +58,13 @@ pub fn draw_displays_tab(ui: &mut egui::Ui, displays: &Arc<Displays>) {
|
||||
|
||||
|
||||
/// Draws a display's geometries
|
||||
pub fn draw_display_geometries(ui: &mut egui::Ui, geometries: &mut Vec<Rect<i32, u32>>) {
|
||||
pub fn draw_display_geometries(ui: &mut egui::Ui, geometries: &mut Vec<DisplayGeometry>) {
|
||||
let mut geometry_idx = 0;
|
||||
geometries.retain_mut(|geometry| {
|
||||
let mut retain = true;
|
||||
ui.horizontal(|ui| {
|
||||
ui.label(format!("#{}: ", geometry_idx + 1));
|
||||
super::draw_rect(ui, geometry);
|
||||
super::draw_rect(ui, geometry.as_rect_mut());
|
||||
if ui.button("-").clicked() {
|
||||
retain = false;
|
||||
}
|
||||
@ -75,6 +75,6 @@ pub fn draw_display_geometries(ui: &mut egui::Ui, geometries: &mut Vec<Rect<i32,
|
||||
});
|
||||
|
||||
if ui.button("+").clicked() {
|
||||
geometries.push(Rect::zero());
|
||||
geometries.push(DisplayGeometry::new(Rect::zero()));
|
||||
}
|
||||
}
|
||||
|
||||
@ -42,7 +42,7 @@ fn draw_panels_editor(ui: &mut egui::Ui, wgpu: &Wgpu, panels: &Panels, window_ge
|
||||
if display
|
||||
.geometries
|
||||
.iter()
|
||||
.all(|&geometry| window_geometry.intersection(geometry).is_none())
|
||||
.all(|&geometry| !geometry.intersects_window(window_geometry))
|
||||
{
|
||||
name = name.weak();
|
||||
}
|
||||
@ -83,12 +83,12 @@ fn draw_fade_panel_editor(
|
||||
for (geometry_idx, geometry) in display.geometries.iter_mut().enumerate() {
|
||||
ui.horizontal(|ui| {
|
||||
let mut name = egui::WidgetText::from(format!("#{}: ", geometry_idx + 1));
|
||||
if window_geometry.intersection(*geometry).is_none() {
|
||||
if !geometry.intersects_window(window_geometry) {
|
||||
name = name.weak();
|
||||
}
|
||||
|
||||
ui.label(name);
|
||||
super::draw_rect(ui, geometry);
|
||||
super::draw_rect(ui, geometry.as_rect_mut());
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
@ -1,13 +1,7 @@
|
||||
//! Panel geometry
|
||||
|
||||
// Imports
|
||||
use {
|
||||
cgmath::{Matrix4, Vector2, Vector3},
|
||||
num_rational::Rational32,
|
||||
std::collections::HashMap,
|
||||
winit::{dpi::PhysicalSize, window::WindowId},
|
||||
zsw_util::Rect,
|
||||
};
|
||||
use {std::collections::HashMap, winit::window::WindowId};
|
||||
|
||||
|
||||
/// Panel geometry
|
||||
@ -33,82 +27,4 @@ impl PanelGeometry {
|
||||
uniforms: HashMap::new(),
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: Move these out of here, since they don't receive `&self`.
|
||||
|
||||
/// Returns this geometry's rectangle for a certain window
|
||||
pub fn geometry_on(display_geometry: Rect<i32, u32>, window_geometry: Rect<i32, u32>) -> Rect<i32, u32> {
|
||||
let mut geometry = display_geometry;
|
||||
geometry.pos -= Vector2::new(window_geometry.pos.x, window_geometry.pos.y);
|
||||
|
||||
geometry
|
||||
}
|
||||
|
||||
/// Calculates this panel's position matrix
|
||||
// Note: This matrix simply goes from a geometry in physical units
|
||||
// onto shader coordinates.
|
||||
#[must_use]
|
||||
pub fn pos_matrix(
|
||||
display_geometry: Rect<i32, u32>,
|
||||
window_geometry: Rect<i32, u32>,
|
||||
surface_size: PhysicalSize<u32>,
|
||||
) -> Matrix4<f32> {
|
||||
let geometry = Self::geometry_on(display_geometry, window_geometry);
|
||||
|
||||
let x_scale = geometry.size[0] as f32 / surface_size.width as f32;
|
||||
let y_scale = geometry.size[1] as f32 / surface_size.height as f32;
|
||||
|
||||
let x_offset = geometry.pos[0] as f32 / surface_size.width as f32;
|
||||
let y_offset = geometry.pos[1] as f32 / surface_size.height as f32;
|
||||
|
||||
let translation = Matrix4::from_translation(Vector3::new(
|
||||
-1.0 + x_scale + 2.0 * x_offset,
|
||||
1.0 - y_scale - 2.0 * y_offset,
|
||||
0.0,
|
||||
));
|
||||
let scaling = Matrix4::from_nonuniform_scale(x_scale, -y_scale, 1.0);
|
||||
translation * scaling
|
||||
}
|
||||
|
||||
/// Calculates an image's ratio for this panel geometry
|
||||
///
|
||||
/// This ratio is multiplied by the base uvs to fix the stretching
|
||||
/// that comes from having a square coordinate system [0.0 .. 1.0] x [0.0 .. 1.0]
|
||||
pub fn image_ratio(panel_size: Vector2<u32>, image_size: Vector2<u32>) -> Vector2<f32> {
|
||||
let image_size = image_size.cast().expect("Image size didn't fit into an `i32`");
|
||||
let panel_size = panel_size.cast().expect("Panel size didn't fit into an `i32`");
|
||||
|
||||
// If either the image or our panel have a side with 0, return a square ratio
|
||||
// TODO: Check if this is the right thing to do
|
||||
if panel_size.x == 0 || panel_size.y == 0 || image_size.x == 0 || image_size.y == 0 {
|
||||
return Vector2::new(0.0, 0.0);
|
||||
}
|
||||
|
||||
// Image and panel ratios
|
||||
let image_ratio = Rational32::new(image_size.x, image_size.y);
|
||||
let panel_ratio = Rational32::new(panel_size.x, panel_size.y);
|
||||
|
||||
// Ratios between the image and panel
|
||||
let width_ratio = Rational32::new(panel_size.x, image_size.x);
|
||||
let height_ratio = Rational32::new(panel_size.y, image_size.y);
|
||||
|
||||
// X-axis ratio, if image scrolls horizontally
|
||||
let x_ratio = self::ratio_as_f32(width_ratio / height_ratio);
|
||||
|
||||
// Y-axis ratio, if image scrolls vertically
|
||||
let y_ratio = self::ratio_as_f32(height_ratio / width_ratio);
|
||||
|
||||
match image_ratio >= panel_ratio {
|
||||
true => Vector2::new(x_ratio, 1.0),
|
||||
false => Vector2::new(1.0, y_ratio),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Converts a `Ratio<i32>` to `f32`, rounding
|
||||
// TODO: Although image and window sizes fit into an `f32`, maybe a
|
||||
// rational of the two wouldn't fit properly when in a num / denom
|
||||
// format, since both may be bigger than `2^24`, check if this is fine.
|
||||
fn ratio_as_f32(ratio: Rational32) -> f32 {
|
||||
*ratio.numer() as f32 / *ratio.denom() as f32
|
||||
}
|
||||
|
||||
@ -12,6 +12,7 @@ use {
|
||||
self::uniform::PanelImageUniforms,
|
||||
super::{PanelGeometryUniforms, PanelState, Panels, state::fade::PanelFadeImagesShared},
|
||||
crate::{
|
||||
display::DisplayGeometry,
|
||||
metrics::{self, Metrics},
|
||||
panel::{PanelGeometry, state::fade::PanelFadeImage},
|
||||
time,
|
||||
@ -252,11 +253,11 @@ impl PanelsRenderer {
|
||||
create_render_pipeline,
|
||||
geometries: HashMap::new(),
|
||||
});
|
||||
for (geometry_idx, (&display_geometry, panel_geometry)) in
|
||||
for (geometry_idx, (display_geometry, panel_geometry)) in
|
||||
display.geometries.iter().zip_eq(&mut panel.geometries).enumerate()
|
||||
{
|
||||
// If this geometry is outside our window, we can safely ignore it
|
||||
if window_geometry.intersection(display_geometry).is_none() {
|
||||
if !display_geometry.intersects_window(window_geometry) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@ -307,12 +308,12 @@ impl PanelsRenderer {
|
||||
panel_state: &PanelState,
|
||||
window_geometry: Rect<i32, u32>,
|
||||
window: &Window,
|
||||
display_geometry: Rect<i32, u32>,
|
||||
display_geometry: &DisplayGeometry,
|
||||
panel_geometry: &mut PanelGeometry,
|
||||
render_pass: &mut wgpu::RenderPass<'_>,
|
||||
) {
|
||||
// Calculate the position matrix for the panel
|
||||
let pos_matrix = PanelGeometry::pos_matrix(display_geometry, window_geometry, surface_size);
|
||||
let pos_matrix = display_geometry.pos_matrix(window_geometry, surface_size);
|
||||
let pos_matrix = uniform::Matrix4x4(pos_matrix.into());
|
||||
|
||||
// Writes uniforms `uniforms`
|
||||
@ -343,7 +344,7 @@ impl PanelsRenderer {
|
||||
},
|
||||
};
|
||||
|
||||
let ratio = PanelGeometry::image_ratio(display_geometry.size, size);
|
||||
let ratio = display_geometry.image_ratio(size);
|
||||
PanelImageUniforms::new(ratio, swap_dir)
|
||||
};
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user