Upstream version 7.36.149.0
[platform/framework/web/crosswalk.git] / src / content / public / android / javatests / src / org / chromium / content / browser / DeviceSensorsTest.java
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;
6
7 import android.content.Context;
8 import android.hardware.Sensor;
9 import android.hardware.SensorEventListener;
10 import android.hardware.SensorManager;
11 import android.os.Handler;
12 import android.test.AndroidTestCase;
13 import android.test.suitebuilder.annotation.SmallTest;
14
15 import java.util.HashSet;
16 import java.util.Set;
17
18 /**
19  * Test suite for DeviceSensors.
20  */
21 public class DeviceSensorsTest extends AndroidTestCase {
22
23     private DeviceSensorsForTests mDeviceSensors;
24     private MockSensorManager mMockSensorManager;
25
26     @Override
27     public void setUp() throws Exception {
28         super.setUp();
29         mMockSensorManager = new MockSensorManager();
30         mDeviceSensors = DeviceSensorsForTests.getInstance(getContext());
31         mDeviceSensors.setSensorManagerProxy(mMockSensorManager);
32     }
33
34     @SmallTest
35     public void testRegisterSensorsDeviceMotion() {
36         boolean start = mDeviceSensors.start(0,
37                 DeviceSensors.DEVICE_MOTION, 100);
38
39         assertTrue(start);
40         assertTrue("should contain all motion sensors",
41                 mDeviceSensors.mActiveSensors.containsAll(
42                         DeviceSensors.DEVICE_MOTION_SENSORS));
43         assertTrue(mDeviceSensors.mDeviceMotionIsActive);
44         assertFalse(mDeviceSensors.mDeviceOrientationIsActive);
45
46         assertEquals(DeviceSensors.DEVICE_MOTION_SENSORS.size(),
47                 mMockSensorManager.numRegistered);
48         assertEquals(0, mMockSensorManager.numUnRegistered);
49         assertEquals(DeviceSensors.DEVICE_MOTION_SENSORS.size(),
50                 mDeviceSensors.getNumberActiveDeviceMotionSensors());
51     }
52
53     @SmallTest
54     public void testRegisterSensorsDeviceOrientation() {
55         boolean start = mDeviceSensors.start(0,
56                 DeviceSensors.DEVICE_ORIENTATION, 100);
57
58         assertTrue(start);
59         assertTrue("should contain all orientation sensors",
60                 mDeviceSensors.mActiveSensors.containsAll(
61                         DeviceSensors.DEVICE_ORIENTATION_SENSORS));
62         assertFalse(mDeviceSensors.mDeviceMotionIsActive);
63         assertTrue(mDeviceSensors.mDeviceOrientationIsActive);
64
65         assertEquals(DeviceSensors.DEVICE_ORIENTATION_SENSORS.size(),
66                 mMockSensorManager.numRegistered);
67         assertEquals(0, mMockSensorManager.numUnRegistered);
68     }
69
70     @SmallTest
71     public void testRegisterSensorsDeviceMotionAndOrientation() {
72         boolean startOrientation = mDeviceSensors.start(0,
73                 DeviceSensors.DEVICE_ORIENTATION, 100);
74         boolean startMotion = mDeviceSensors.start(0,
75                 DeviceSensors.DEVICE_MOTION, 100);
76
77         assertTrue(startOrientation);
78         assertTrue(startMotion);
79         assertTrue("should contain all motion sensors",
80                 mDeviceSensors.mActiveSensors.containsAll(
81                         DeviceSensors.DEVICE_MOTION_SENSORS));
82         assertTrue("should contain all orientation sensors",
83                 mDeviceSensors.mActiveSensors.containsAll(
84                         DeviceSensors.DEVICE_ORIENTATION_SENSORS));
85
86         Set<Integer> union = new HashSet<Integer>(
87             DeviceSensors.DEVICE_ORIENTATION_SENSORS);
88         union.addAll(DeviceSensors.DEVICE_MOTION_SENSORS);
89
90         assertEquals(union.size(), mDeviceSensors.mActiveSensors.size());
91         assertTrue(mDeviceSensors.mDeviceMotionIsActive);
92         assertTrue(mDeviceSensors.mDeviceOrientationIsActive);
93         assertEquals(union.size(), mMockSensorManager.numRegistered);
94         assertEquals(0, mMockSensorManager.numUnRegistered);
95         assertEquals(DeviceSensors.DEVICE_MOTION_SENSORS.size(),
96                 mDeviceSensors.getNumberActiveDeviceMotionSensors());
97     }
98
99     @SmallTest
100     public void testUnregisterSensorsDeviceMotion() {
101         mDeviceSensors.start(0, DeviceSensors.DEVICE_MOTION, 100);
102         mDeviceSensors.stop(DeviceSensors.DEVICE_MOTION);
103
104         assertTrue("should contain no sensors",
105                 mDeviceSensors.mActiveSensors.isEmpty());
106         assertFalse(mDeviceSensors.mDeviceMotionIsActive);
107         assertFalse(mDeviceSensors.mDeviceOrientationIsActive);
108         assertEquals(DeviceSensors.DEVICE_MOTION_SENSORS.size(),
109                 mMockSensorManager.numUnRegistered);
110         assertEquals(0, mDeviceSensors.getNumberActiveDeviceMotionSensors());
111     }
112
113     @SmallTest
114     public void testUnregisterSensorsDeviceOrientation() {
115         mDeviceSensors.start(0, DeviceSensors.DEVICE_ORIENTATION, 100);
116         mDeviceSensors.stop(DeviceSensors.DEVICE_ORIENTATION);
117
118         assertTrue("should contain no sensors",
119                 mDeviceSensors.mActiveSensors.isEmpty());
120         assertFalse(mDeviceSensors.mDeviceMotionIsActive);
121         assertFalse(mDeviceSensors.mDeviceOrientationIsActive);
122         assertEquals(DeviceSensors.DEVICE_ORIENTATION_SENSORS.size(),
123                 mMockSensorManager.numUnRegistered);
124     }
125
126     @SmallTest
127     public void testUnRegisterSensorsDeviceMotionAndOrientation() {
128         mDeviceSensors.start(0, DeviceSensors.DEVICE_ORIENTATION, 100);
129         mDeviceSensors.start(0, DeviceSensors.DEVICE_MOTION, 100);
130         mDeviceSensors.stop(DeviceSensors.DEVICE_MOTION);
131
132         assertTrue("should contain all orientation sensors",
133                 mDeviceSensors.mActiveSensors.containsAll(
134                         DeviceSensors.DEVICE_ORIENTATION_SENSORS));
135
136         Set<Integer> diff = new HashSet<Integer>(DeviceSensors.DEVICE_MOTION_SENSORS);
137         diff.removeAll(DeviceSensors.DEVICE_ORIENTATION_SENSORS);
138
139         assertEquals(diff.size(), mMockSensorManager.numUnRegistered);
140
141         mDeviceSensors.stop(DeviceSensors.DEVICE_ORIENTATION);
142
143         assertTrue("should contain no sensors",
144                 mDeviceSensors.mActiveSensors.isEmpty());
145         assertEquals(diff.size() + DeviceSensors.DEVICE_ORIENTATION_SENSORS.size(),
146                 mMockSensorManager.numUnRegistered);
147         assertEquals(0, mDeviceSensors.getNumberActiveDeviceMotionSensors());
148     }
149
150     @SmallTest
151     public void testSensorChangedgotOrientation() {
152         boolean startOrientation = mDeviceSensors.start(0,
153                 DeviceSensors.DEVICE_ORIENTATION, 100);
154
155         assertTrue(startOrientation);
156         assertTrue(mDeviceSensors.mDeviceOrientationIsActive);
157
158         float alpha = (float) Math.PI / 4;
159         float[] values = {0, 0, (float) Math.sin(alpha / 2), (float) Math.cos(alpha / 2), -1};
160         mDeviceSensors.sensorChanged(Sensor.TYPE_ROTATION_VECTOR, values);
161         mDeviceSensors.verifyCalls("gotOrientation");
162         mDeviceSensors.verifyValuesEpsilon(Math.toDegrees(alpha), 0, 0);
163     }
164
165     @SmallTest
166     public void testSensorChangedgotAccelerationIncludingGravity() {
167         mDeviceSensors.start(0, DeviceSensors.DEVICE_MOTION, 100);
168
169         float[] values = {1, 2, 3};
170         mDeviceSensors.sensorChanged(Sensor.TYPE_ACCELEROMETER, values);
171         mDeviceSensors.verifyCalls("gotAccelerationIncludingGravity");
172         mDeviceSensors.verifyValues(1, 2, 3);
173     }
174
175     @SmallTest
176     public void testSensorChangedgotAcceleration() {
177         mDeviceSensors.start(0, DeviceSensors.DEVICE_MOTION, 100);
178
179         float[] values = {1, 2, 3};
180         mDeviceSensors.sensorChanged(Sensor.TYPE_LINEAR_ACCELERATION, values);
181         mDeviceSensors.verifyCalls("gotAcceleration");
182         mDeviceSensors.verifyValues(1, 2, 3);
183     }
184
185     @SmallTest
186     public void testSensorChangedgotRotationRate() {
187         mDeviceSensors.start(0, DeviceSensors.DEVICE_MOTION, 100);
188
189         float[] values = {1, 2, 3};
190         mDeviceSensors.sensorChanged(Sensor.TYPE_GYROSCOPE, values);
191         mDeviceSensors.verifyCalls("gotRotationRate");
192         mDeviceSensors.verifyValues(1, 2, 3);
193     }
194
195     @SmallTest
196     public void testSensorChangedgotOrientationAndAcceleration() {
197         boolean startOrientation = mDeviceSensors.start(0,
198                 DeviceSensors.DEVICE_ORIENTATION, 100);
199         boolean startMotion = mDeviceSensors.start(0,
200                 DeviceSensors.DEVICE_MOTION, 100);
201
202         assertTrue(startOrientation);
203         assertTrue(startMotion);
204         assertTrue(mDeviceSensors.mDeviceMotionIsActive);
205         assertTrue(mDeviceSensors.mDeviceOrientationIsActive);
206
207         float alpha = (float) Math.PI / 4;
208         float[] values = {0, 0, (float) Math.sin(alpha / 2), (float) Math.cos(alpha / 2), -1};
209         mDeviceSensors.sensorChanged(Sensor.TYPE_ROTATION_VECTOR, values);
210         mDeviceSensors.verifyCalls("gotOrientation");
211         mDeviceSensors.verifyValuesEpsilon(Math.toDegrees(alpha), 0, 0);
212
213         float[] values2 = {1, 2, 3};
214         mDeviceSensors.sensorChanged(Sensor.TYPE_ACCELEROMETER, values2);
215         mDeviceSensors.verifyCalls("gotOrientation" +
216                 "gotAccelerationIncludingGravity");
217         mDeviceSensors.verifyValues(1, 2, 3);
218     }
219
220
221     // Tests for correct Device Orientation angles.
222
223     @SmallTest
224     public void testOrientationAnglesFromRotationMatrixIdentity() {
225         float[] gravity = {0, 0, 1};
226         float[] magnetic = {0, 1, 0};
227         double[] expectedAngles = {0, 0, 0};
228
229         verifyOrientationAngles(gravity, magnetic, expectedAngles);
230     }
231
232     @SmallTest
233     public void testOrientationAnglesFromRotationMatrix45DegreesX() {
234         float[] gravity = {0, (float) Math.sin(Math.PI / 4), (float) Math.cos(Math.PI / 4)};
235         float[] magnetic = {0, 1, 0};
236         double[] expectedAngles = {0, Math.PI / 4, 0};
237
238         verifyOrientationAngles(gravity, magnetic, expectedAngles);
239     }
240
241     @SmallTest
242     public void testOrientationAnglesFromRotationMatrix45DegreesY() {
243         float[] gravity = {-(float) Math.sin(Math.PI / 4), 0, (float) Math.cos(Math.PI / 4)};
244         float[] magnetic = {0, 1, 0};
245         double[] expectedAngles = {0, 0, Math.PI / 4};
246
247         verifyOrientationAngles(gravity, magnetic, expectedAngles);
248     }
249
250     @SmallTest
251     public void testOrientationAnglesFromRotationMatrix45DegreesZ() {
252         float[] gravity = {0, 0, 1};
253         float[] magnetic = {(float) Math.sin(Math.PI / 4), (float) Math.cos(Math.PI / 4), 0};
254         double[] expectedAngles = {Math.PI / 4, 0, 0};
255
256         verifyOrientationAngles(gravity, magnetic, expectedAngles);
257     }
258
259     @SmallTest
260     public void testOrientationAnglesFromRotationMatrixGimbalLock() {
261         float[] gravity = {0, 1, 0};
262         float[] magnetic = {(float) Math.sin(Math.PI / 4), 0, -(float) Math.cos(Math.PI / 4)};
263         double[] expectedAngles = {Math.PI / 4, Math.PI / 2, 0};  // favor yaw instead of roll
264
265         verifyOrientationAngles(gravity, magnetic, expectedAngles);
266     }
267
268     @SmallTest
269     public void testOrientationAnglesFromRotationMatrixPitchGreaterThan90() {
270         final double largePitchAngle = Math.PI / 2 + Math.PI / 4;
271         float[] gravity = {0, (float) Math.cos(largePitchAngle - Math.PI / 2),
272                 -(float) Math.sin(largePitchAngle - Math.PI / 2)};
273         float[] magnetic = {0, 0, -1};
274         double[] expectedAngles = {0, largePitchAngle, 0};
275
276         verifyOrientationAngles(gravity, magnetic, expectedAngles);
277     }
278
279     @SmallTest
280     public void testOrientationAnglesFromRotationMatrixRoll90() {
281         float[] gravity = {-1, 0, 0};
282         float[] magnetic = {0, 1, 0};
283         double[] expectedAngles = {Math.PI, -Math.PI, -Math.PI / 2};
284
285         verifyOrientationAngles(gravity, magnetic, expectedAngles);
286     }
287
288     /**
289      * Helper method for verifying angles obtained from rotation matrix.
290      *
291      * @param gravity
292      *        gravity vector in the device frame
293      * @param magnetic
294      *        magnetic field vector in the device frame
295      * @param expectedAngles
296      *        expectedAngles[0] rotation angle in radians around the Z-axis
297      *        expectedAngles[1] rotation angle in radians around the X-axis
298      *        expectedAngles[2] rotation angle in radians around the Y-axis
299      */
300     private void verifyOrientationAngles(float[] gravity, float[] magnetic,
301             double[] expectedAngles) {
302         float[] R = new float[9];
303         double[] values = new double[3];
304         SensorManager.getRotationMatrix(R, null, gravity, magnetic);
305         mDeviceSensors.computeDeviceOrientationFromRotationMatrix(R, values);
306
307         assertEquals(expectedAngles.length, values.length);
308         final double epsilon = 0.001;
309         for (int i = 0; i < expectedAngles.length; ++i) {
310             assertEquals(expectedAngles[i], values[i], epsilon);
311         }
312
313     }
314
315     // -- End Tests for correct Device Orientation angles.
316
317     private static class DeviceSensorsForTests extends DeviceSensors {
318
319         private double value1 = 0;
320         private double value2 = 0;
321         private double value3 = 0;
322         private String mCalls = "";
323
324         private DeviceSensorsForTests(Context context) {
325             super(context);
326         }
327
328         static DeviceSensorsForTests getInstance(Context context) {
329             return new DeviceSensorsForTests(context);
330         }
331
332         private void verifyValues(double v1, double v2, double v3) {
333             assertEquals(v1, value1);
334             assertEquals(v2, value2);
335             assertEquals(v3, value3);
336         }
337
338         private void verifyValuesEpsilon(double v1, double v2, double v3) {
339             assertEquals(v1, value1, 0.1);
340             assertEquals(v2, value2, 0.1);
341             assertEquals(v3, value3, 0.1);
342         }
343
344         private void verifyCalls(String names) {
345             assertEquals(mCalls, names);
346         }
347
348         @Override
349         protected void gotOrientation(double alpha, double beta, double gamma) {
350             value1 = alpha;
351             value2 = beta;
352             value3 = gamma;
353             mCalls = mCalls.concat("gotOrientation");
354         }
355
356         @Override
357         protected void gotAcceleration(double x, double y, double z) {
358             value1 = x;
359             value2 = y;
360             value3 = z;
361             mCalls = mCalls.concat("gotAcceleration");
362         }
363
364         @Override
365         protected void gotAccelerationIncludingGravity(double x, double y, double z) {
366             value1 = x;
367             value2 = y;
368             value3 = z;
369             mCalls = mCalls.concat("gotAccelerationIncludingGravity");
370         }
371
372         @Override
373         protected void gotRotationRate(double alpha, double beta, double gamma) {
374             value1 = alpha;
375             value2 = beta;
376             value3 = gamma;
377             mCalls = mCalls.concat("gotRotationRate");
378         }
379     }
380
381     private static class MockSensorManager implements
382             DeviceSensors.SensorManagerProxy {
383
384         private int numRegistered = 0;
385         private int numUnRegistered = 0;
386
387         private MockSensorManager() {
388         }
389
390         @Override
391         public boolean registerListener(SensorEventListener listener, int sensorType, int rate,
392                 Handler handler) {
393             numRegistered++;
394             return true;
395         }
396
397         @Override
398         public void unregisterListener(SensorEventListener listener, int sensorType) {
399             numUnRegistered++;
400         }
401     }
402 }