dioxus_html/events/
wheel.rs1use dioxus_core::Event;
2use std::fmt::Formatter;
3
4use crate::geometry::*;
5use crate::input_data::{MouseButton, MouseButtonSet};
6use crate::prelude::*;
7
8use super::HasMouseData;
9
10pub type WheelEvent = Event<WheelData>;
13
14pub struct WheelData {
16 inner: Box<dyn HasWheelData>,
17}
18
19impl<E: HasWheelData> From<E> for WheelData {
20 fn from(e: E) -> Self {
21 Self { inner: Box::new(e) }
22 }
23}
24
25impl std::fmt::Debug for WheelData {
26 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
27 f.debug_struct("WheelData")
28 .field("delta", &self.delta())
29 .field("coordinates", &self.coordinates())
30 .field("modifiers", &self.modifiers())
31 .field("held_buttons", &self.held_buttons())
32 .field("trigger_button", &self.trigger_button())
33 .finish()
34 }
35}
36
37impl PartialEq for WheelData {
38 fn eq(&self, other: &Self) -> bool {
39 self.inner.delta() == other.inner.delta()
40 }
41}
42
43impl WheelData {
44 pub fn new(inner: impl HasWheelData + 'static) -> Self {
45 Self {
46 inner: Box::new(inner),
47 }
48 }
49
50 #[allow(deprecated)]
52 pub fn delta(&self) -> WheelDelta {
53 self.inner.delta()
54 }
55
56 #[inline(always)]
58 pub fn downcast<T: 'static>(&self) -> Option<&T> {
59 HasWheelData::as_any(&*self.inner).downcast_ref::<T>()
60 }
61}
62
63impl InteractionLocation for WheelData {
64 fn client_coordinates(&self) -> ClientPoint {
65 self.inner.client_coordinates()
66 }
67
68 fn page_coordinates(&self) -> PagePoint {
69 self.inner.page_coordinates()
70 }
71
72 fn screen_coordinates(&self) -> ScreenPoint {
73 self.inner.screen_coordinates()
74 }
75}
76
77impl InteractionElementOffset for WheelData {
78 fn element_coordinates(&self) -> ElementPoint {
79 self.inner.element_coordinates()
80 }
81
82 fn coordinates(&self) -> Coordinates {
83 self.inner.coordinates()
84 }
85}
86
87impl ModifiersInteraction for WheelData {
88 fn modifiers(&self) -> Modifiers {
89 self.inner.modifiers()
90 }
91}
92
93impl PointerInteraction for WheelData {
94 fn held_buttons(&self) -> MouseButtonSet {
95 self.inner.held_buttons()
96 }
97
98 fn trigger_button(&self) -> Option<MouseButton> {
100 self.inner.trigger_button()
101 }
102}
103
104#[cfg(feature = "serialize")]
105#[derive(serde::Serialize, serde::Deserialize, Debug, PartialEq, Clone)]
107pub struct SerializedWheelData {
108 #[serde(flatten)]
109 pub mouse: crate::point_interaction::SerializedPointInteraction,
110
111 pub delta_mode: u32,
112 pub delta_x: f64,
113 pub delta_y: f64,
114 pub delta_z: f64,
115}
116
117#[cfg(feature = "serialize")]
118impl SerializedWheelData {
119 pub fn new(wheel: &WheelData) -> Self {
121 let delta_mode = match wheel.delta() {
122 WheelDelta::Pixels(_) => 0,
123 WheelDelta::Lines(_) => 1,
124 WheelDelta::Pages(_) => 2,
125 };
126 let delta_raw = wheel.delta().strip_units();
127 Self {
128 mouse: crate::point_interaction::SerializedPointInteraction::from(wheel),
129 delta_mode,
130 delta_x: delta_raw.x,
131 delta_y: delta_raw.y,
132 delta_z: delta_raw.z,
133 }
134 }
135}
136
137#[cfg(feature = "serialize")]
138impl From<&WheelData> for SerializedWheelData {
139 fn from(data: &WheelData) -> Self {
140 Self::new(data)
141 }
142}
143
144#[cfg(feature = "serialize")]
145impl HasWheelData for SerializedWheelData {
146 fn delta(&self) -> WheelDelta {
147 WheelDelta::from_web_attributes(self.delta_mode, self.delta_x, self.delta_y, self.delta_z)
148 }
149
150 fn as_any(&self) -> &dyn std::any::Any {
151 self
152 }
153}
154
155#[cfg(feature = "serialize")]
156impl HasMouseData for SerializedWheelData {
157 fn as_any(&self) -> &dyn std::any::Any {
158 self
159 }
160}
161
162#[cfg(feature = "serialize")]
163impl InteractionLocation for SerializedWheelData {
164 fn client_coordinates(&self) -> ClientPoint {
165 self.mouse.client_coordinates()
166 }
167
168 fn page_coordinates(&self) -> PagePoint {
169 self.mouse.page_coordinates()
170 }
171
172 fn screen_coordinates(&self) -> ScreenPoint {
173 self.mouse.screen_coordinates()
174 }
175}
176
177#[cfg(feature = "serialize")]
178impl InteractionElementOffset for SerializedWheelData {
179 fn element_coordinates(&self) -> ElementPoint {
180 self.mouse.element_coordinates()
181 }
182
183 fn coordinates(&self) -> Coordinates {
184 self.mouse.coordinates()
185 }
186}
187
188#[cfg(feature = "serialize")]
189impl ModifiersInteraction for SerializedWheelData {
190 fn modifiers(&self) -> Modifiers {
191 self.mouse.modifiers()
192 }
193}
194
195#[cfg(feature = "serialize")]
196impl PointerInteraction for SerializedWheelData {
197 fn held_buttons(&self) -> MouseButtonSet {
198 self.mouse.held_buttons()
199 }
200
201 fn trigger_button(&self) -> Option<MouseButton> {
202 self.mouse.trigger_button()
203 }
204}
205
206#[cfg(feature = "serialize")]
207impl serde::Serialize for WheelData {
208 fn serialize<S: serde::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
209 SerializedWheelData::from(self).serialize(serializer)
210 }
211}
212
213#[cfg(feature = "serialize")]
214impl<'de> serde::Deserialize<'de> for WheelData {
215 fn deserialize<D: serde::Deserializer<'de>>(deserializer: D) -> Result<Self, D::Error> {
216 let data = SerializedWheelData::deserialize(deserializer)?;
217 Ok(Self {
218 inner: Box::new(data),
219 })
220 }
221}
222
223impl_event![
224 WheelData;
225
226 onwheel
228];
229
230pub trait HasWheelData: HasMouseData + std::any::Any {
231 fn delta(&self) -> WheelDelta;
233
234 fn as_any(&self) -> &dyn std::any::Any;
236}