blob: 9e697db5c1e8c54690caf3c97f2b344fd766965d [file] [log] [blame]
Jeff Browne839a582010-04-22 18:58:52 -07001//
2// Copyright 2010 The Android Open Source Project
3//
4// Provides a pipe-based transport for native events in the NDK.
5//
6#define LOG_TAG "Input"
7
8//#define LOG_NDEBUG 0
9
Jeff Brown66888372010-11-29 17:37:49 -080010#define DEBUG_PROBE 0
11
12#include <stdlib.h>
13#include <unistd.h>
14
Jeff Browne839a582010-04-22 18:58:52 -070015#include <ui/Input.h>
16
17namespace android {
18
Jeff Brown66888372010-11-29 17:37:49 -080019static const char* CONFIGURATION_FILE_DIR[] = {
20 "idc/",
21 "keylayout/",
22 "keychars/",
23};
24
25static const char* CONFIGURATION_FILE_EXTENSION[] = {
26 ".idc",
27 ".kl",
28 ".kcm",
29};
30
31static void appendInputDeviceConfigurationFileRelativePath(String8& path,
32 const String8& name, InputDeviceConfigurationFileType type) {
33 path.append(CONFIGURATION_FILE_DIR[type]);
34 for (size_t i = 0; i < name.length(); i++) {
35 char ch = name[i];
36 if (ch == ' ') {
37 ch = '_';
38 }
39 path.append(&ch, 1);
40 }
41 path.append(CONFIGURATION_FILE_EXTENSION[type]);
42}
43
44extern String8 getInputDeviceConfigurationFilePath(
45 const String8& name, InputDeviceConfigurationFileType type) {
46 // Search system repository.
47 String8 path;
48 path.setTo(getenv("ANDROID_ROOT"));
49 path.append("/usr/");
50 appendInputDeviceConfigurationFileRelativePath(path, name, type);
51#if DEBUG_PROBE
52 LOGD("Probing for system provided input device configuration file: path='%s'", path.string());
53#endif
54 if (!access(path.string(), R_OK)) {
55#if DEBUG_PROBE
56 LOGD("Found");
57#endif
58 return path;
59 }
60
61 // Search user repository.
62 // TODO Should only look here if not in safe mode.
63 path.setTo(getenv("ANDROID_DATA"));
64 path.append("/system/devices/");
65 appendInputDeviceConfigurationFileRelativePath(path, name, type);
66#if DEBUG_PROBE
67 LOGD("Probing for system user input device configuration file: path='%s'", path.string());
68#endif
69 if (!access(path.string(), R_OK)) {
70#if DEBUG_PROBE
71 LOGD("Found");
72#endif
73 return path;
74 }
75
76 // Not found.
77#if DEBUG_PROBE
78 LOGD("Probe failed to find input device configuration file: name='%s', type=%d",
79 name.string(), type);
80#endif
81 return String8();
82}
83
84
85// --- InputEvent ---
Jeff Browne839a582010-04-22 18:58:52 -070086
Jeff Brown5c1ed842010-07-14 18:48:53 -070087void InputEvent::initialize(int32_t deviceId, int32_t source) {
Jeff Browne839a582010-04-22 18:58:52 -070088 mDeviceId = deviceId;
Jeff Brown5c1ed842010-07-14 18:48:53 -070089 mSource = source;
Jeff Browne839a582010-04-22 18:58:52 -070090}
91
Dianne Hackborn0e885272010-07-15 17:44:53 -070092void InputEvent::initialize(const InputEvent& from) {
93 mDeviceId = from.mDeviceId;
94 mSource = from.mSource;
95}
96
Jeff Brown66888372010-11-29 17:37:49 -080097// --- KeyEvent ---
Jeff Browne839a582010-04-22 18:58:52 -070098
Dianne Hackborn189ed232010-06-29 19:20:40 -070099bool KeyEvent::hasDefaultAction(int32_t keyCode) {
100 switch (keyCode) {
Jeff Brown8575a872010-06-30 16:10:35 -0700101 case AKEYCODE_HOME:
102 case AKEYCODE_BACK:
103 case AKEYCODE_CALL:
104 case AKEYCODE_ENDCALL:
105 case AKEYCODE_VOLUME_UP:
106 case AKEYCODE_VOLUME_DOWN:
Jeff Brown7e5660f2010-11-01 15:24:01 -0700107 case AKEYCODE_VOLUME_MUTE:
Jeff Brown8575a872010-06-30 16:10:35 -0700108 case AKEYCODE_POWER:
109 case AKEYCODE_CAMERA:
110 case AKEYCODE_HEADSETHOOK:
111 case AKEYCODE_MENU:
112 case AKEYCODE_NOTIFICATION:
113 case AKEYCODE_FOCUS:
114 case AKEYCODE_SEARCH:
Jeff Brown7e5660f2010-11-01 15:24:01 -0700115 case AKEYCODE_MEDIA_PLAY:
116 case AKEYCODE_MEDIA_PAUSE:
Jeff Brown8575a872010-06-30 16:10:35 -0700117 case AKEYCODE_MEDIA_PLAY_PAUSE:
118 case AKEYCODE_MEDIA_STOP:
119 case AKEYCODE_MEDIA_NEXT:
120 case AKEYCODE_MEDIA_PREVIOUS:
121 case AKEYCODE_MEDIA_REWIND:
Jeff Brown7e5660f2010-11-01 15:24:01 -0700122 case AKEYCODE_MEDIA_RECORD:
Jeff Brown8575a872010-06-30 16:10:35 -0700123 case AKEYCODE_MEDIA_FAST_FORWARD:
124 case AKEYCODE_MUTE:
Dianne Hackborn189ed232010-06-29 19:20:40 -0700125 return true;
126 }
127
128 return false;
129}
130
131bool KeyEvent::hasDefaultAction() const {
132 return hasDefaultAction(getKeyCode());
133}
134
135bool KeyEvent::isSystemKey(int32_t keyCode) {
136 switch (keyCode) {
Jeff Brown8575a872010-06-30 16:10:35 -0700137 case AKEYCODE_MENU:
138 case AKEYCODE_SOFT_RIGHT:
139 case AKEYCODE_HOME:
140 case AKEYCODE_BACK:
141 case AKEYCODE_CALL:
142 case AKEYCODE_ENDCALL:
143 case AKEYCODE_VOLUME_UP:
144 case AKEYCODE_VOLUME_DOWN:
Jeff Brown7e5660f2010-11-01 15:24:01 -0700145 case AKEYCODE_VOLUME_MUTE:
Jeff Brown8575a872010-06-30 16:10:35 -0700146 case AKEYCODE_MUTE:
147 case AKEYCODE_POWER:
148 case AKEYCODE_HEADSETHOOK:
Jeff Brown7e5660f2010-11-01 15:24:01 -0700149 case AKEYCODE_MEDIA_PLAY:
150 case AKEYCODE_MEDIA_PAUSE:
Jeff Brown8575a872010-06-30 16:10:35 -0700151 case AKEYCODE_MEDIA_PLAY_PAUSE:
152 case AKEYCODE_MEDIA_STOP:
153 case AKEYCODE_MEDIA_NEXT:
154 case AKEYCODE_MEDIA_PREVIOUS:
155 case AKEYCODE_MEDIA_REWIND:
Jeff Brown7e5660f2010-11-01 15:24:01 -0700156 case AKEYCODE_MEDIA_RECORD:
Jeff Brown8575a872010-06-30 16:10:35 -0700157 case AKEYCODE_MEDIA_FAST_FORWARD:
158 case AKEYCODE_CAMERA:
159 case AKEYCODE_FOCUS:
160 case AKEYCODE_SEARCH:
Dianne Hackborn189ed232010-06-29 19:20:40 -0700161 return true;
162 }
163
164 return false;
165}
166
167bool KeyEvent::isSystemKey() const {
168 return isSystemKey(getKeyCode());
169}
170
Jeff Browne839a582010-04-22 18:58:52 -0700171void KeyEvent::initialize(
172 int32_t deviceId,
Jeff Brown5c1ed842010-07-14 18:48:53 -0700173 int32_t source,
Jeff Browne839a582010-04-22 18:58:52 -0700174 int32_t action,
175 int32_t flags,
176 int32_t keyCode,
177 int32_t scanCode,
178 int32_t metaState,
179 int32_t repeatCount,
180 nsecs_t downTime,
181 nsecs_t eventTime) {
Jeff Brown5c1ed842010-07-14 18:48:53 -0700182 InputEvent::initialize(deviceId, source);
Jeff Browne839a582010-04-22 18:58:52 -0700183 mAction = action;
184 mFlags = flags;
185 mKeyCode = keyCode;
186 mScanCode = scanCode;
187 mMetaState = metaState;
188 mRepeatCount = repeatCount;
189 mDownTime = downTime;
190 mEventTime = eventTime;
191}
192
Dianne Hackborn0e885272010-07-15 17:44:53 -0700193void KeyEvent::initialize(const KeyEvent& from) {
194 InputEvent::initialize(from);
195 mAction = from.mAction;
196 mFlags = from.mFlags;
197 mKeyCode = from.mKeyCode;
198 mScanCode = from.mScanCode;
199 mMetaState = from.mMetaState;
200 mRepeatCount = from.mRepeatCount;
201 mDownTime = from.mDownTime;
202 mEventTime = from.mEventTime;
203}
204
Jeff Brown66888372010-11-29 17:37:49 -0800205// --- MotionEvent ---
Jeff Browne839a582010-04-22 18:58:52 -0700206
207void MotionEvent::initialize(
208 int32_t deviceId,
Jeff Brown5c1ed842010-07-14 18:48:53 -0700209 int32_t source,
Jeff Browne839a582010-04-22 18:58:52 -0700210 int32_t action,
Jeff Brownaf30ff62010-09-01 17:01:00 -0700211 int32_t flags,
Jeff Browne839a582010-04-22 18:58:52 -0700212 int32_t edgeFlags,
213 int32_t metaState,
Jeff Brownf4a4ec22010-06-16 01:53:36 -0700214 float xOffset,
215 float yOffset,
Jeff Browne839a582010-04-22 18:58:52 -0700216 float xPrecision,
217 float yPrecision,
218 nsecs_t downTime,
219 nsecs_t eventTime,
220 size_t pointerCount,
221 const int32_t* pointerIds,
222 const PointerCoords* pointerCoords) {
Jeff Brown5c1ed842010-07-14 18:48:53 -0700223 InputEvent::initialize(deviceId, source);
Jeff Browne839a582010-04-22 18:58:52 -0700224 mAction = action;
Jeff Brownaf30ff62010-09-01 17:01:00 -0700225 mFlags = flags;
Jeff Browne839a582010-04-22 18:58:52 -0700226 mEdgeFlags = edgeFlags;
227 mMetaState = metaState;
Jeff Brownf4a4ec22010-06-16 01:53:36 -0700228 mXOffset = xOffset;
229 mYOffset = yOffset;
Jeff Browne839a582010-04-22 18:58:52 -0700230 mXPrecision = xPrecision;
231 mYPrecision = yPrecision;
232 mDownTime = downTime;
233 mPointerIds.clear();
234 mPointerIds.appendArray(pointerIds, pointerCount);
235 mSampleEventTimes.clear();
236 mSamplePointerCoords.clear();
237 addSample(eventTime, pointerCoords);
238}
239
240void MotionEvent::addSample(
241 int64_t eventTime,
242 const PointerCoords* pointerCoords) {
243 mSampleEventTimes.push(eventTime);
244 mSamplePointerCoords.appendArray(pointerCoords, getPointerCount());
245}
246
247void MotionEvent::offsetLocation(float xOffset, float yOffset) {
Jeff Brownf4a4ec22010-06-16 01:53:36 -0700248 mXOffset += xOffset;
249 mYOffset += yOffset;
Jeff Browne839a582010-04-22 18:58:52 -0700250}
251
Jeff Brown66888372010-11-29 17:37:49 -0800252// --- InputDeviceInfo ---
Jeff Browne57e8952010-07-23 21:28:06 -0700253
254InputDeviceInfo::InputDeviceInfo() {
255 initialize(-1, String8("uninitialized device info"));
256}
257
258InputDeviceInfo::InputDeviceInfo(const InputDeviceInfo& other) :
259 mId(other.mId), mName(other.mName), mSources(other.mSources),
260 mKeyboardType(other.mKeyboardType),
261 mMotionRanges(other.mMotionRanges) {
262}
263
264InputDeviceInfo::~InputDeviceInfo() {
265}
266
267void InputDeviceInfo::initialize(int32_t id, const String8& name) {
268 mId = id;
269 mName = name;
270 mSources = 0;
271 mKeyboardType = AINPUT_KEYBOARD_TYPE_NONE;
272 mMotionRanges.clear();
273}
274
275const InputDeviceInfo::MotionRange* InputDeviceInfo::getMotionRange(int32_t rangeType) const {
276 ssize_t index = mMotionRanges.indexOfKey(rangeType);
277 return index >= 0 ? & mMotionRanges.valueAt(index) : NULL;
278}
279
280void InputDeviceInfo::addSource(uint32_t source) {
281 mSources |= source;
282}
283
284void InputDeviceInfo::addMotionRange(int32_t rangeType, float min, float max,
285 float flat, float fuzz) {
286 MotionRange range = { min, max, flat, fuzz };
287 addMotionRange(rangeType, range);
288}
289
290void InputDeviceInfo::addMotionRange(int32_t rangeType, const MotionRange& range) {
291 mMotionRanges.add(rangeType, range);
292}
293
Jeff Browne839a582010-04-22 18:58:52 -0700294} // namespace android