dioxus_html/events/
pointer.rs1use dioxus_core::Event;
2use keyboard_types::Modifiers;
3
4use crate::{geometry::*, input_data::*, *};
5
6pub type PointerEvent = Event<PointerData>;
8
9pub struct PointerData {
10 inner: Box<dyn HasPointerData>,
11}
12
13impl PointerData {
14 pub fn new(data: impl HasPointerData + 'static) -> Self {
16 Self::from(data)
17 }
18
19 #[inline(always)]
21 pub fn downcast<T: 'static>(&self) -> Option<&T> {
22 self.inner.as_any().downcast_ref::<T>()
23 }
24}
25
26impl<E: HasPointerData + 'static> From<E> for PointerData {
27 fn from(e: E) -> Self {
28 Self { inner: Box::new(e) }
29 }
30}
31
32impl std::fmt::Debug for PointerData {
33 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
34 f.debug_struct("PointerData")
35 .field("pointer_id", &self.pointer_id())
36 .field("width", &self.width())
37 .field("height", &self.height())
38 .field("pressure", &self.pressure())
39 .field("tangential_pressure", &self.tangential_pressure())
40 .field("tilt_x", &self.tilt_x())
41 .field("tilt_y", &self.tilt_y())
42 .field("twist", &self.twist())
43 .field("pointer_type", &self.pointer_type())
44 .field("is_primary", &self.is_primary())
45 .field("coordinates", &self.coordinates())
46 .field("modifiers", &self.modifiers())
47 .field("held_buttons", &self.held_buttons())
48 .field("trigger_button", &self.trigger_button())
49 .finish()
50 }
51}
52
53impl PartialEq for PointerData {
54 fn eq(&self, other: &Self) -> bool {
55 self.pointer_id() == other.pointer_id()
56 && self.width() == other.width()
57 && self.height() == other.height()
58 && self.pressure() == other.pressure()
59 && self.tangential_pressure() == other.tangential_pressure()
60 && self.tilt_x() == other.tilt_x()
61 && self.tilt_y() == other.tilt_y()
62 && self.twist() == other.twist()
63 && self.pointer_type() == other.pointer_type()
64 && self.is_primary() == other.is_primary()
65 && self.coordinates() == other.coordinates()
66 && self.modifiers() == other.modifiers()
67 && self.held_buttons() == other.held_buttons()
68 && self.trigger_button() == other.trigger_button()
69 }
70}
71
72pub trait HasPointerData: PointerInteraction {
74 fn pointer_id(&self) -> i32;
76
77 fn width(&self) -> f64;
79
80 fn height(&self) -> f64;
82
83 fn pressure(&self) -> f32;
85
86 fn tangential_pressure(&self) -> f32;
88
89 fn tilt_x(&self) -> i32;
91
92 fn tilt_y(&self) -> i32;
94
95 fn twist(&self) -> i32;
97
98 fn pointer_type(&self) -> String;
100
101 fn is_primary(&self) -> bool;
103
104 fn as_any(&self) -> &dyn std::any::Any;
106}
107
108impl_event![
109 PointerData;
110 onpointerdown
112
113 onpointermove
115
116 onpointerup
118
119 onpointercancel
121
122 ongotpointercapture
124
125 onlostpointercapture
127
128 onpointerenter
130
131 onpointerleave
133
134 onpointerover
136
137 onpointerout
139
140 onauxclick
142];
143
144impl PointerData {
145 pub fn pointer_id(&self) -> i32 {
147 self.inner.pointer_id()
148 }
149
150 pub fn width(&self) -> f64 {
152 self.inner.width()
153 }
154
155 pub fn height(&self) -> f64 {
157 self.inner.height()
158 }
159
160 pub fn pressure(&self) -> f32 {
162 self.inner.pressure()
163 }
164
165 pub fn tangential_pressure(&self) -> f32 {
167 self.inner.tangential_pressure()
168 }
169
170 pub fn tilt_x(&self) -> i32 {
172 self.inner.tilt_x()
173 }
174
175 pub fn tilt_y(&self) -> i32 {
177 self.inner.tilt_y()
178 }
179
180 pub fn twist(&self) -> i32 {
182 self.inner.twist()
183 }
184
185 pub fn pointer_type(&self) -> String {
187 self.inner.pointer_type()
188 }
189
190 pub fn is_primary(&self) -> bool {
192 self.inner.is_primary()
193 }
194}
195
196impl InteractionLocation for PointerData {
197 fn client_coordinates(&self) -> ClientPoint {
198 self.inner.client_coordinates()
199 }
200
201 fn screen_coordinates(&self) -> ScreenPoint {
202 self.inner.screen_coordinates()
203 }
204
205 fn page_coordinates(&self) -> PagePoint {
206 self.inner.page_coordinates()
207 }
208}
209
210impl InteractionElementOffset for PointerData {
211 fn element_coordinates(&self) -> ElementPoint {
212 self.inner.element_coordinates()
213 }
214}
215
216impl ModifiersInteraction for PointerData {
217 fn modifiers(&self) -> Modifiers {
218 self.inner.modifiers()
219 }
220}
221
222impl PointerInteraction for PointerData {
223 fn held_buttons(&self) -> MouseButtonSet {
224 self.inner.held_buttons()
225 }
226
227 fn trigger_button(&self) -> Option<MouseButton> {
228 self.inner.trigger_button()
229 }
230}
231
232#[cfg(feature = "serialize")]
233#[derive(serde::Serialize, serde::Deserialize, Debug, PartialEq, Clone)]
235pub struct SerializedPointerData {
236 #[serde(flatten)]
238 point_data: crate::point_interaction::SerializedPointInteraction,
239
240 pointer_id: i32,
242
243 width: f64,
245
246 height: f64,
248
249 pressure: f32,
251
252 tangential_pressure: f32,
254
255 tilt_x: i32,
257
258 tilt_y: i32,
260
261 twist: i32,
263
264 pointer_type: String,
266
267 is_primary: bool,
269}
270
271#[cfg(feature = "serialize")]
272impl HasPointerData for SerializedPointerData {
273 fn pointer_id(&self) -> i32 {
274 self.pointer_id
275 }
276
277 fn width(&self) -> f64 {
278 self.width
279 }
280
281 fn height(&self) -> f64 {
282 self.height
283 }
284
285 fn pressure(&self) -> f32 {
286 self.pressure
287 }
288
289 fn tangential_pressure(&self) -> f32 {
290 self.tangential_pressure
291 }
292
293 fn tilt_x(&self) -> i32 {
294 self.tilt_x
295 }
296
297 fn tilt_y(&self) -> i32 {
298 self.tilt_y
299 }
300
301 fn twist(&self) -> i32 {
302 self.twist
303 }
304
305 fn pointer_type(&self) -> String {
306 self.pointer_type.clone()
307 }
308
309 fn is_primary(&self) -> bool {
310 self.is_primary
311 }
312
313 fn as_any(&self) -> &dyn std::any::Any {
314 self
315 }
316}
317
318#[cfg(feature = "serialize")]
319impl InteractionLocation for SerializedPointerData {
320 fn client_coordinates(&self) -> ClientPoint {
321 self.point_data.client_coordinates()
322 }
323
324 fn screen_coordinates(&self) -> ScreenPoint {
325 self.point_data.screen_coordinates()
326 }
327
328 fn page_coordinates(&self) -> PagePoint {
329 self.point_data.page_coordinates()
330 }
331}
332
333#[cfg(feature = "serialize")]
334impl InteractionElementOffset for SerializedPointerData {
335 fn element_coordinates(&self) -> ElementPoint {
336 self.point_data.element_coordinates()
337 }
338}
339
340#[cfg(feature = "serialize")]
341impl ModifiersInteraction for SerializedPointerData {
342 fn modifiers(&self) -> Modifiers {
343 self.point_data.modifiers()
344 }
345}
346
347#[cfg(feature = "serialize")]
348impl PointerInteraction for SerializedPointerData {
349 fn held_buttons(&self) -> MouseButtonSet {
350 self.point_data.held_buttons()
351 }
352
353 fn trigger_button(&self) -> Option<MouseButton> {
354 self.point_data.trigger_button()
355 }
356}
357
358#[cfg(feature = "serialize")]
359impl From<&PointerData> for SerializedPointerData {
360 fn from(data: &PointerData) -> Self {
361 Self {
362 point_data: data.into(),
363 pointer_id: data.pointer_id(),
364 width: data.width(),
365 height: data.height(),
366 pressure: data.pressure(),
367 tangential_pressure: data.tangential_pressure(),
368 tilt_x: data.tilt_x(),
369 tilt_y: data.tilt_y(),
370 twist: data.twist(),
371 pointer_type: data.pointer_type().to_string(),
372 is_primary: data.is_primary(),
373 }
374 }
375}
376
377#[cfg(feature = "serialize")]
378impl serde::Serialize for PointerData {
379 fn serialize<S: serde::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
380 SerializedPointerData::from(self).serialize(serializer)
381 }
382}
383
384#[cfg(feature = "serialize")]
385impl<'de> serde::Deserialize<'de> for PointerData {
386 fn deserialize<D: serde::Deserializer<'de>>(deserializer: D) -> Result<Self, D::Error> {
387 let data = SerializedPointerData::deserialize(deserializer)?;
388 Ok(Self {
389 inner: Box::new(data),
390 })
391 }
392}