comparison src/uinput.rs @ 12:d43c31aff57c

Split uinput helpers into another module.
author Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
date Sun, 01 Nov 2020 16:01:00 +0100
parents
children 478cf2a7d577
comparison
equal deleted inserted replaced
11:0193041f01d4 12:d43c31aff57c
1 // Tablet emulator, for people who don’t own one
2 // Copyright © 2020 Emmanuel Gil Peyrot <linkmauve@linkmauve.fr>
3 //
4 // This program is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU Affero General Public License as published by
6 // the Free Software Foundation, either version 3 of the License, or
7 // (at your option) any later version.
8 //
9 // This program is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU Affero General Public License for more details.
13 //
14 // You should have received a copy of the GNU Affero General Public License
15 // along with this program. If not, see <https://www.gnu.org/licenses/>.
16
17 use std::fs::{File, OpenOptions};
18 use crate::{MAX_X, MAX_Y};
19 use input_linux::{
20 sys::input_event, sys::timeval, AbsoluteAxis, AbsoluteInfo, AbsoluteInfoSetup, EventKind,
21 InputId, InputProperty, Key, MiscKind, SynchronizeKind, UInputHandle,
22 };
23
24 pub fn create_uinput_device() -> std::io::Result<UInputHandle<File>> {
25 let file = OpenOptions::new().write(true).open("/dev/uinput")?;
26 let dev = UInputHandle::new(file);
27
28 dev.set_evbit(EventKind::Synchronize)?;
29 dev.set_evbit(EventKind::Key)?;
30 dev.set_evbit(EventKind::Absolute)?;
31 dev.set_evbit(EventKind::Misc)?;
32 dev.set_keybit(Key::ButtonToolPen)?;
33 dev.set_keybit(Key::ButtonToolRubber)?;
34 dev.set_keybit(Key::ButtonToolBrush)?;
35 dev.set_keybit(Key::ButtonToolPencil)?;
36 dev.set_keybit(Key::ButtonToolAirbrush)?;
37 dev.set_keybit(Key::ButtonTouch)?;
38 dev.set_keybit(Key::ButtonStylus)?;
39 dev.set_keybit(Key::ButtonStylus2)?;
40 dev.set_keybit(Key::ButtonStylus3)?;
41 dev.set_mscbit(MiscKind::Serial)?;
42 dev.set_propbit(InputProperty::Direct)?;
43
44 dev.set_absbit(AbsoluteAxis::X)?;
45 dev.set_absbit(AbsoluteAxis::Y)?;
46 dev.set_absbit(AbsoluteAxis::Z)?;
47 dev.set_absbit(AbsoluteAxis::Wheel)?;
48 dev.set_absbit(AbsoluteAxis::Pressure)?;
49 dev.set_absbit(AbsoluteAxis::Distance)?;
50 dev.set_absbit(AbsoluteAxis::TiltX)?;
51 dev.set_absbit(AbsoluteAxis::TiltY)?;
52 dev.set_absbit(AbsoluteAxis::Misc)?;
53
54 let id = InputId {
55 bustype: 3,
56 vendor: 0x56a,
57 product: 0x350,
58 version: 0xb,
59 };
60
61 let x = AbsoluteInfoSetup {
62 axis: AbsoluteAxis::X,
63 info: AbsoluteInfo {
64 value: 0,
65 minimum: 0,
66 maximum: MAX_X,
67 fuzz: 0,
68 flat: 0,
69 resolution: 200,
70 },
71 };
72 let y = AbsoluteInfoSetup {
73 axis: AbsoluteAxis::Y,
74 info: AbsoluteInfo {
75 value: 0,
76 minimum: 0,
77 maximum: MAX_Y,
78 fuzz: 0,
79 flat: 0,
80 resolution: 200,
81 },
82 };
83 let z = AbsoluteInfoSetup {
84 axis: AbsoluteAxis::Z,
85 info: AbsoluteInfo {
86 value: 0,
87 minimum: -900,
88 maximum: 899,
89 fuzz: 0,
90 flat: 0,
91 resolution: 287,
92 },
93 };
94 let wheel = AbsoluteInfoSetup {
95 axis: AbsoluteAxis::Wheel,
96 info: AbsoluteInfo {
97 value: 0,
98 minimum: 0,
99 maximum: 2047,
100 fuzz: 0,
101 flat: 0,
102 resolution: 0,
103 },
104 };
105 let pressure = AbsoluteInfoSetup {
106 axis: AbsoluteAxis::Pressure,
107 info: AbsoluteInfo {
108 value: 0,
109 minimum: 0,
110 maximum: 8196,
111 fuzz: 0,
112 flat: 0,
113 resolution: 0,
114 },
115 };
116 let distance = AbsoluteInfoSetup {
117 axis: AbsoluteAxis::Distance,
118 info: AbsoluteInfo {
119 value: 0,
120 minimum: 0,
121 maximum: 63,
122 fuzz: 0,
123 flat: 0,
124 resolution: 0,
125 },
126 };
127 let tilt_x = AbsoluteInfoSetup {
128 axis: AbsoluteAxis::TiltX,
129 info: AbsoluteInfo {
130 value: 0,
131 minimum: -64,
132 maximum: 63,
133 fuzz: 0,
134 flat: 0,
135 resolution: 57,
136 },
137 };
138 let tilt_y = AbsoluteInfoSetup {
139 axis: AbsoluteAxis::TiltY,
140 info: AbsoluteInfo {
141 value: 0,
142 minimum: -64,
143 maximum: 63,
144 fuzz: 0,
145 flat: 0,
146 resolution: 57,
147 },
148 };
149 let misc = AbsoluteInfoSetup {
150 axis: AbsoluteAxis::Misc,
151 info: AbsoluteInfo {
152 value: 0,
153 minimum: 0,
154 maximum: 0,
155 fuzz: 0,
156 flat: 0,
157 resolution: 0,
158 },
159 };
160
161 dev.create(
162 &id,
163 b"TabletEmu",
164 0,
165 &[x, y, z, wheel, pressure, distance, tilt_x, tilt_y, misc],
166 )?;
167 Ok(dev)
168 }
169
170 fn input_event_new(type_: EventKind, code: u16, value: i32) -> input_event {
171 input_event {
172 time: timeval {
173 tv_sec: 0,
174 tv_usec: 0,
175 },
176 type_: type_ as u16,
177 code,
178 value,
179 }
180 }
181
182 pub fn input_axis_new(code: AbsoluteAxis, value: i32) -> input_event {
183 input_event_new(EventKind::Absolute, code as u16, value)
184 }
185
186 pub fn input_key_new(code: Key, value: i32) -> input_event {
187 input_event_new(EventKind::Key, code as u16, value)
188 }
189
190 pub fn input_misc_new(code: MiscKind, value: i32) -> input_event {
191 input_event_new(EventKind::Misc, code as u16, value)
192 }
193
194 pub fn input_synchronize_new(code: SynchronizeKind, value: i32) -> input_event {
195 input_event_new(EventKind::Synchronize, code as u16, value)
196 }