kobo_core/device/
touch.rs1pub const SWIPE_MIN_DX: f32 = 80.0;
11pub const SWIPE_MAX_MS: u128 = 500;
12pub const DOUBLE_TAP_MAX_PRESS_MS: u128 = 300;
13pub const DOUBLE_TAP_WINDOW_MS: u128 = 400;
14
15#[derive(Clone, Copy)]
17pub struct TouchConfig {
18 pub switch_xy: bool,
19 pub mirrored_x: bool,
20 pub mirrored_y: bool,
21 pub raw_x_max: i32,
22 pub raw_y_max: i32,
23 pub screen_w: i32,
24 pub screen_h: i32,
25}
26
27pub fn to_display(rx: i32, ry: i32, cfg: &TouchConfig) -> (f32, f32) {
29 let (mut x, mut y) = if cfg.switch_xy { (ry, rx) } else { (rx, ry) };
30
31 if cfg.mirrored_x {
32 let max = if cfg.switch_xy {
33 cfg.raw_y_max
34 } else {
35 cfg.raw_x_max
36 };
37 x = max - x;
38 }
39 if cfg.mirrored_y {
40 let max = if cfg.switch_xy {
41 cfg.raw_x_max
42 } else {
43 cfg.raw_y_max
44 };
45 y = max - y;
46 }
47
48 (x as f32, y as f32)
49}
50
51#[allow(dead_code)]
52pub fn is_swipe(swipe_dx: f32, swipe_dy: f32, dt_ms: u128) -> bool {
53 swipe_dx.abs() > SWIPE_MIN_DX && dt_ms < SWIPE_MAX_MS && swipe_dx.abs() > swipe_dy.abs()
54}
55
56pub fn is_double_tap(dt_ms: u128, since_prev_tap_ms: u128) -> bool {
57 dt_ms < DOUBLE_TAP_MAX_PRESS_MS && since_prev_tap_ms < DOUBLE_TAP_WINDOW_MS
58}
59
60#[cfg(test)]
61mod tests {
62 use super::*;
63
64 fn libra_cfg() -> TouchConfig {
66 TouchConfig {
67 switch_xy: true,
68 mirrored_x: true,
69 mirrored_y: false,
70 raw_x_max: 1447,
71 raw_y_max: 1071,
72 screen_w: 1072,
73 screen_h: 1448,
74 }
75 }
76
77 fn plain_cfg() -> TouchConfig {
79 TouchConfig {
80 switch_xy: false,
81 mirrored_x: false,
82 mirrored_y: false,
83 raw_x_max: 1071,
84 raw_y_max: 1447,
85 screen_w: 1072,
86 screen_h: 1448,
87 }
88 }
89
90 #[test]
91 fn libra_left_edge_maps_small_x() {
92 let cfg = libra_cfg();
93 let (dx, _) = to_display(736, 1035, &cfg);
94 assert!(
95 dx < 100.0,
96 "left-edge tap must map to small display_x, got {dx}"
97 );
98 }
99
100 #[test]
101 fn libra_right_edge_maps_large_x() {
102 let cfg = libra_cfg();
103 let (dx, _) = to_display(693, 36, &cfg);
104 assert!(
105 dx > 970.0,
106 "right-edge tap must map to large display_x, got {dx}"
107 );
108 }
109
110 #[test]
111 fn plain_passes_through() {
112 let cfg = plain_cfg();
113 let (dx, dy) = to_display(100, 200, &cfg);
114 assert_eq!(dx, 100.0);
115 assert_eq!(dy, 200.0);
116 }
117
118 #[test]
119 fn plain_mirrored_x() {
120 let mut cfg = plain_cfg();
121 cfg.mirrored_x = true;
122 let (dx, _) = to_display(0, 0, &cfg);
123 assert_eq!(dx, cfg.raw_x_max as f32);
124 }
125
126 #[test]
127 fn is_swipe_detects_fast_horizontal_flick() {
128 assert!(is_swipe(200.0, 5.0, 120));
129 assert!(is_swipe(-250.0, 40.0, 200));
130 }
131
132 #[test]
133 fn is_swipe_rejects_small_or_slow_or_vertical() {
134 assert!(!is_swipe(20.0, 5.0, 300));
135 assert!(!is_swipe(200.0, 5.0, 600));
136 assert!(!is_swipe(100.0, 300.0, 100));
137 }
138
139 #[test]
140 fn is_double_tap_within_window() {
141 assert!(is_double_tap(150, 200));
142 assert!(!is_double_tap(400, 200));
143 assert!(!is_double_tap(150, 500));
144 }
145}