OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 package org.chromium.content.browser.input; | |
6 | |
7 import android.util.SparseArray; | |
8 import android.view.KeyEvent; | |
9 import android.view.MotionEvent; | |
10 | |
11 import org.chromium.base.JNINamespace; | |
12 import org.chromium.content.browser.input.gamepad_mapping.CanonicalAxisIndex; | |
13 import org.chromium.content.browser.input.gamepad_mapping.CanonicalButtonIndex; | |
14 | |
15 /** | |
16 * Device specific input data converter for Gamepad API. | |
17 * Implemented per device by subclasses. | |
18 */ | |
19 @JNINamespace("content") | |
20 abstract class GamepadDataMapper { | |
21 protected static final String PS3_SIXAXIS_DEVICE_NAME = "Sony PLAYSTATION(R) 3 Controller"; | |
22 | |
23 public abstract WebGamepadData map(SparseArray<Float> axes, SparseArray<Bool ean> buttons); | |
Ted C
2014/03/07 20:18:09
per my comment about object creation in the other
kbalazs
2014/03/12 00:17:36
Done, I hold the object in the mapper now.
| |
24 | |
25 // Factory method. | |
26 public static GamepadDataMapper createDataMapper(String deviceName) { | |
27 if (deviceName.equals(PS3_SIXAXIS_DEVICE_NAME)) | |
28 return new PS3SixAxisGamepadDataMapper(); | |
29 | |
30 return new GenericGamepadDataMapper(deviceName); | |
31 } | |
32 | |
33 protected static float axisValue(Float f) { return f == null ? 0 : f.floatVa lue(); } | |
34 protected static float buttonValue(Boolean b) { return (b == null || !b) ? 0 : 1; } | |
35 | |
36 protected static WebGamepadData createWebGamepadData() { | |
37 WebGamepadData data = new WebGamepadData(); | |
38 data.axes = new float[CanonicalAxisIndex.NUM_CANONICAL_AXES]; | |
39 data.buttons = new float[CanonicalButtonIndex.NUM_CANONICAL_BUTTONS]; | |
40 return data; | |
41 } | |
42 | |
43 protected static void mapCommonXYAxes(WebGamepadData data, SparseArray<Float > axes) { | |
44 Float x = (Float) axes.get(MotionEvent.AXIS_X); | |
Ted C
2014/03/07 20:18:09
get on a typed SparseArray should mean that you do
kbalazs
2014/03/07 22:40:22
Right, but unfortunately there is no such thing as
Ted C
2014/03/08 01:06:00
My previous comment was that calling .get() on a S
| |
45 Float y = (Float) axes.get(MotionEvent.AXIS_Y); | |
46 data.axes[CanonicalAxisIndex.AXIS_LEFT_STICK_X] = axisValue(x); | |
47 data.axes[CanonicalAxisIndex.AXIS_LEFT_STICK_Y] = axisValue(y); | |
48 } | |
49 | |
50 protected static void mapCommonTriggerAxes(WebGamepadData data, SparseArray< Float> axes) { | |
51 Float lTrigger = (Float) axes.get(MotionEvent.AXIS_LTRIGGER); | |
52 Float rTrigger = (Float) axes.get(MotionEvent.AXIS_RTRIGGER); | |
53 data.buttons[CanonicalButtonIndex.BUTTON_LEFT_SHOULDER] = axisValue(lTri gger); | |
54 data.buttons[CanonicalButtonIndex.BUTTON_RIGHT_SHOULDER] = axisValue(rTr igger); | |
55 } | |
56 | |
57 protected static void mapCommonTriggerButtons( | |
58 WebGamepadData data, SparseArray<Boolean> buttons) { | |
59 Boolean l1 = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_L1); | |
60 Boolean r1 = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_R1); | |
61 data.buttons[CanonicalButtonIndex.BUTTON_LEFT_TRIGGER] = buttonValue(l1) ; | |
62 data.buttons[CanonicalButtonIndex.BUTTON_RIGHT_TRIGGER] = buttonValue(r1 ); | |
63 } | |
64 | |
65 protected static void mapCommonThumbstickButtons( | |
66 WebGamepadData data, SparseArray<Boolean> buttons) { | |
67 Boolean thumbL = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_THUMBL); | |
68 Boolean thumbR = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_THUMBR); | |
69 data.buttons[CanonicalButtonIndex.BUTTON_LEFT_THUMBSTICK] = buttonValue( thumbL); | |
70 data.buttons[CanonicalButtonIndex.BUTTON_RIGHT_THUMBSTICK] = buttonValue (thumbR); | |
71 } | |
72 | |
73 protected static void mapCommonStartSelectButtons( | |
74 WebGamepadData data, SparseArray<Boolean> buttons) { | |
75 Boolean select = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_SELECT); | |
76 Boolean start = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_START); | |
77 data.buttons[CanonicalButtonIndex.BUTTON_BACK_SELECT] = buttonValue(sele ct); | |
78 data.buttons[CanonicalButtonIndex.BUTTON_START] = buttonValue(start); | |
79 } | |
80 | |
81 protected static void mapCommonDpadButtons( | |
82 WebGamepadData data, SparseArray<Boolean> buttons) { | |
83 Boolean dpadDown = (Boolean) buttons.get(KeyEvent.KEYCODE_DPAD_DOWN); | |
84 Boolean dpadUp = (Boolean) buttons.get(KeyEvent.KEYCODE_DPAD_UP); | |
85 Boolean dpadLeft = (Boolean) buttons.get(KeyEvent.KEYCODE_DPAD_LEFT); | |
86 Boolean dpadRight = (Boolean) buttons.get(KeyEvent.KEYCODE_DPAD_RIGHT); | |
87 data.buttons[CanonicalButtonIndex.BUTTON_DPAD_DOWN] = buttonValue(dpadDo wn); | |
88 data.buttons[CanonicalButtonIndex.BUTTON_DPAD_UP] = buttonValue(dpadUp); | |
89 data.buttons[CanonicalButtonIndex.BUTTON_DPAD_LEFT] = buttonValue(dpadLe ft); | |
90 data.buttons[CanonicalButtonIndex.BUTTON_DPAD_RIGHT] = buttonValue(dpadR ight); | |
91 } | |
92 | |
93 protected static void mapCommonXYABButtons( | |
94 WebGamepadData data, SparseArray<Boolean> buttons) { | |
95 Boolean bA = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_A); | |
96 Boolean bB = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_B); | |
97 Boolean bX = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_X); | |
98 Boolean bY = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_Y); | |
99 data.buttons[CanonicalButtonIndex.BUTTON_PRIMARY] = buttonValue(bA); | |
100 data.buttons[CanonicalButtonIndex.BUTTON_SECONDARY] = buttonValue(bB); | |
101 data.buttons[CanonicalButtonIndex.BUTTON_TERTIARY] = buttonValue(bX); | |
102 data.buttons[CanonicalButtonIndex.BUTTON_QUATERNARY] = buttonValue(bY); | |
103 } | |
104 } | |
105 | |
106 // This is a last resort if we find a device that we don't know about. | |
107 // The Android API is general enough that this can be better than nothing | |
108 // but we should not really rely on this. | |
109 class GenericGamepadDataMapper extends GamepadDataMapper { | |
110 private final String mDeviceName; | |
111 | |
112 GenericGamepadDataMapper(String deviceName) { | |
113 mDeviceName = deviceName; | |
114 } | |
115 | |
116 // Find something for right stick x and y. If there is even more axes, map t hem to | |
117 // non-canonical positions. | |
118 private static void mapRightAndExtraSticks(WebGamepadData data, SparseArray< Float> axes) { | |
119 int position = CanonicalAxisIndex.AXIS_RIGHT_STICK_X; | |
120 // position + 1 is AXIS_RIGHT_STICK_Y. | |
121 Float x = (Float) axes.get(MotionEvent.AXIS_RX); | |
122 Float y = (Float) axes.get(MotionEvent.AXIS_RY); | |
123 if (x != null || y != null) { | |
124 data.axes[position++] = axisValue(x); | |
125 data.axes[position++] = axisValue(y); | |
126 } | |
127 x = (Float) axes.get(MotionEvent.AXIS_Z); | |
128 y = (Float) axes.get(MotionEvent.AXIS_RZ); | |
129 if (x != null || y != null) { | |
130 data.axes[position++] = axisValue(x); | |
131 data.axes[position++] = axisValue(y); | |
132 } | |
133 x = (Float) axes.get(MotionEvent.AXIS_HAT_X); | |
134 y = (Float) axes.get(MotionEvent.AXIS_HAT_Y); | |
135 if (x != null || y != null) { | |
136 data.axes[position++] = axisValue(x); | |
137 data.axes[position++] = axisValue(y); | |
138 } | |
Ted C
2014/03/07 20:18:09
This doesn't verify axes size is large enough. Mi
kbalazs
2014/03/07 22:40:22
Right, I overlooked it.
kbalazs
2014/03/12 00:17:36
Done.
| |
139 } | |
140 | |
141 public WebGamepadData map(SparseArray<Float> axes, SparseArray<Boolean> butt ons) { | |
142 WebGamepadData data = createWebGamepadData(); | |
143 data.id = mDeviceName + " (STANDARD_GAMEPAD)"; | |
144 data.mapping = "standard"; | |
145 mapCommonXYAxes(data, axes); | |
146 mapRightAndExtraSticks(data, axes); | |
147 mapCommonTriggerAxes(data, axes); | |
148 mapCommonXYABButtons(data, buttons); | |
149 mapCommonTriggerButtons(data, buttons); | |
150 mapCommonThumbstickButtons(data, buttons); | |
151 mapCommonStartSelectButtons(data, buttons); | |
152 mapCommonDpadButtons(data, buttons); | |
153 | |
154 // TODO(b.kelemen): meta is missing. | |
155 | |
156 return data; | |
157 } | |
158 } | |
159 | |
160 class PS3SixAxisGamepadDataMapper extends GamepadDataMapper { | |
161 public WebGamepadData map(SparseArray<Float> axes, SparseArray<Boolean> butt ons) { | |
162 WebGamepadData data = createWebGamepadData(); | |
163 data.id = PS3_SIXAXIS_DEVICE_NAME + " (STANDARD_GAMEPAD)"; | |
Ted C
2014/03/07 20:18:09
I would make " (STANDARD_GAMEPAD)" and "standard"
kbalazs
2014/03/12 00:17:36
Done.
| |
164 data.mapping = "standard"; | |
165 | |
166 mapCommonXYAxes(data, axes); | |
167 | |
168 Float z = (Float) axes.get(MotionEvent.AXIS_Z); | |
169 Float rz = (Float) axes.get(MotionEvent.AXIS_RZ); | |
170 data.axes[CanonicalAxisIndex.AXIS_RIGHT_STICK_X] = axisValue(z); | |
171 data.axes[CanonicalAxisIndex.AXIS_RIGHT_STICK_Y] = axisValue(rz); | |
172 | |
173 mapCommonTriggerAxes(data, axes); | |
174 | |
175 Boolean bA = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_A); | |
176 Boolean bB = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_B); | |
177 Boolean bX = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_X); | |
178 Boolean bY = (Boolean) buttons.get(KeyEvent.KEYCODE_BUTTON_Y); | |
179 data.buttons[CanonicalButtonIndex.BUTTON_PRIMARY] = buttonValue(bX); | |
180 data.buttons[CanonicalButtonIndex.BUTTON_SECONDARY] = buttonValue(bY); | |
181 data.buttons[CanonicalButtonIndex.BUTTON_TERTIARY] = buttonValue(bA); | |
182 data.buttons[CanonicalButtonIndex.BUTTON_QUATERNARY] = buttonValue(bB); | |
183 | |
184 mapCommonTriggerButtons(data, buttons); | |
185 mapCommonThumbstickButtons(data, buttons); | |
186 mapCommonStartSelectButtons(data, buttons); | |
187 mapCommonDpadButtons(data, buttons); | |
188 | |
189 // TODO(b.kelemen): PS button is missing. Looks like it is swallowed by Android | |
190 // but probably there is a way to configure otherwise and in this case w e should | |
191 // handle it. | |
192 | |
193 return data; | |
194 } | |
195 } | |
196 | |
197 // TODO(b.kelemen): add more implementations. It would be nice to support at lea st those that are | |
198 // supported on Linux. | |
OLD | NEW |