1 /*
2  * Copyright (C) 2011 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package com.android.cts.verifier.sensors;
18 
19 import com.android.cts.verifier.PassFailButtons;
20 import com.android.cts.verifier.R;
21 import com.android.cts.verifier.sensors.renderers.GLRotationGuideRenderer;
22 
23 import android.app.AlertDialog;
24 import android.content.Intent;
25 import android.hardware.Sensor;
26 import android.hardware.SensorEvent;
27 import android.hardware.SensorEventListener;
28 import android.hardware.SensorManager;
29 import android.opengl.GLSurfaceView;
30 import android.os.Bundle;
31 import android.view.View;
32 import android.view.View.OnClickListener;
33 import android.widget.TextView;
34 
35 /**
36  * Manual test for testing the gyroscope sensor. This test consists of 6 steps for all the
37  * different ways to rotate the device along the x, y, and z axis. It also raises a warning
38  * if the values seem to high and may be degrees.
39  *
40  * @deprecated It has been replaced by {@link GyroscopeMeasurementTestActivity}
41  */
42 @Deprecated
43 public class GyroscopeTestActivity extends PassFailButtons.Activity {
44 
45     private static final int NUM_STAGES = 6;
46     private static final String STAGE_INDEX_EXTRA = "stageIndex";
47 
48     private SensorManager mSensorManager;
49     private Sensor mSensor;
50     private SensorListener mSensorListener;
51     private GLSurfaceView mGLSurfaceView;
52     private GLRotationGuideRenderer mRenderer;
53     private TextView mProgressText;
54     private TextView mSensorText;
55 
56     private AlertDialog mNoGyroscopeWarningDialog;
57     private AlertDialog mDegreesWarningDialog;
58 
59     @Override
onCreate(Bundle savedInstanceState)60     protected void onCreate(Bundle savedInstanceState) {
61         super.onCreate(savedInstanceState);
62         setContentView(R.layout.snsr_gyro);
63         setInfoResources(R.string.snsr_gyro_test, R.string.snsr_gyro_test_info, 0);
64         setPassFailButtonClickListeners();
65 
66         // This activity is reused 6 times with different settings to test each rotation direction
67         final int stageIndex = getIntent().getIntExtra(STAGE_INDEX_EXTRA, 0);
68         Settings settings = getSettings(stageIndex);
69 
70         // Hitting the pass button goes to the next test activity. Only the last one ends the test.
71         if (stageIndex + 1 < NUM_STAGES) {
72             setPassButtonGoesToNextStage(stageIndex);
73         }
74 
75         mSensorManager = (SensorManager) getSystemService(SENSOR_SERVICE);
76         mSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE);
77         mSensorListener = new SensorListener(settings.mSensorEventIndex,
78                 settings.mExpectPositiveValue);
79 
80         mGLSurfaceView = (GLSurfaceView) findViewById(R.id.gl_surface_view);
81         mRenderer = new GLRotationGuideRenderer();
82         mRenderer.setRotation(settings.mRotateX, settings.mRotateY, settings.mRotateZ);
83         mGLSurfaceView.setRenderer(mRenderer);
84 
85         mProgressText = (TextView) findViewById(R.id.progress);
86         mProgressText.setText(String.format(getString(R.string.snsr_gyro_test_progress),
87                 settings.mStageIndex + 1, settings.mTotalStages));
88 
89         mSensorText = (TextView) findViewById(R.id.sensor_value);
90     }
91 
getSettings(int stageIndex)92     private Settings getSettings(int stageIndex) {
93         switch (stageIndex) {
94             case 0:
95                 return new Settings(stageIndex, NUM_STAGES, 0, 0, 1, 2, true);
96             case 1:
97                 return new Settings(stageIndex, NUM_STAGES, 0, 0, -1, 2, false);
98             case 2:
99                 return new Settings(stageIndex, NUM_STAGES, 0, 1, 0, 1, true);
100             case 3:
101                 return new Settings(stageIndex, NUM_STAGES, 0, -1, 0, 1, false);
102             case 4:
103                 return new Settings(stageIndex, NUM_STAGES, 1, 0, 0, 0, true);
104             case 5:
105                 return new Settings(stageIndex, NUM_STAGES, -1, 0, 0, 0, false);
106             default:
107                 throw new IllegalArgumentException("Bad stage index: " + stageIndex);
108         }
109     }
110 
111     /** Bundle of settings for testing a certain rotation direction. */
112     class Settings {
113         int mStageIndex;
114         int mTotalStages;
115         float mRotateX;
116         float mRotateY;
117         float mRotateZ;
118         int mSensorEventIndex;
119         boolean mExpectPositiveValue;
120 
Settings(int stageIndex, int totalStages, float rotateX, float rotateY, float rotateZ, int sensorEventIndex, boolean expectPositiveValue)121         Settings(int stageIndex, int totalStages, float rotateX, float rotateY, float rotateZ,
122                 int sensorEventIndex, boolean expectPositiveValue) {
123             mStageIndex = stageIndex;
124             mTotalStages = totalStages;
125             mRotateX = rotateX;
126             mRotateY = rotateY;
127             mRotateZ = rotateZ;
128             mSensorEventIndex = sensorEventIndex;
129             mExpectPositiveValue = expectPositiveValue;
130         }
131     }
132 
setPassButtonGoesToNextStage(final int stageIndex)133     private void setPassButtonGoesToNextStage(final int stageIndex) {
134         findViewById(R.id.pass_button).setOnClickListener(new OnClickListener() {
135             @Override
136             public void onClick(View v) {
137                 Intent intent = new Intent(GyroscopeTestActivity.this,
138                         GyroscopeTestActivity.class);
139                 intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP
140                         | Intent.FLAG_ACTIVITY_FORWARD_RESULT);
141                 intent.putExtra(STAGE_INDEX_EXTRA, stageIndex + 1);
142                 startActivity(intent);
143             }
144         });
145     }
146 
147     @Override
onResume()148     protected void onResume() {
149         super.onResume();
150         if (!mSensorManager.registerListener(mSensorListener, mSensor,
151                 SensorManager.SENSOR_DELAY_UI)) {
152             showNoGyroscopeWarningDialog();
153         }
154     }
155 
156     @Override
onPause()157     protected void onPause() {
158         super.onPause();
159         mSensorManager.unregisterListener(mSensorListener, mSensor);
160     }
161 
162     class SensorListener implements SensorEventListener {
163 
164         /** Throw away other events that are smaller than this. */
165         private static final double MOVING_AMOUNT = 0.1;
166 
167         private final int mEventIndex;
168 
169         private final boolean mExpectPositive;
170 
SensorListener(int eventIndex, boolean expectPositive)171         SensorListener(int eventIndex, boolean expectPositive) {
172             mEventIndex = eventIndex;
173             mExpectPositive = expectPositive;
174         }
175 
176         @Override
onSensorChanged(SensorEvent event)177         public void onSensorChanged(SensorEvent event) {
178             float value = event.values[mEventIndex];
179             if (value > MOVING_AMOUNT) {
180                 if (mExpectPositive) {
181                     updateWidgets(
182                             value,
183                             GLRotationGuideRenderer.BACKGROUND_GREEN,
184                             R.drawable.fs_good);
185                 } else {
186                     updateWidgets(
187                             value,
188                             GLRotationGuideRenderer.BACKGROUND_RED,
189                             R.drawable.fs_error);
190                 }
191             } else if (value < -MOVING_AMOUNT) {
192                 if (mExpectPositive) {
193                     updateWidgets(
194                             value,
195                             GLRotationGuideRenderer.BACKGROUND_RED,
196                             R.drawable.fs_error);
197                 } else {
198                     updateWidgets(
199                             value,
200                             GLRotationGuideRenderer.BACKGROUND_GREEN,
201                             R.drawable.fs_good);
202                 }
203             } else {
204                 updateWidgets(
205                         value,
206                         GLRotationGuideRenderer.BACKGROUND_BLACK,
207                         R.drawable.fs_indeterminate);
208             }
209 
210             if (value > 10) {
211                 showDegreesWarningDialog();
212             }
213         }
214 
updateWidgets(float sensorValue, int backgroundColor, int icon)215         void updateWidgets(float sensorValue, int backgroundColor, int icon) {
216             synchronized (GyroscopeTestActivity.this) {
217                 mRenderer.setBackgroundColor(backgroundColor);
218             }
219             mSensorText.setText(String.format("%+.2f", sensorValue));
220             mSensorText.setCompoundDrawablesWithIntrinsicBounds(0, 0, icon, 0);
221         }
222 
223         @Override
onAccuracyChanged(Sensor sensor, int accuracy)224         public void onAccuracyChanged(Sensor sensor, int accuracy) {
225         }
226     }
227 
showNoGyroscopeWarningDialog()228     private void showNoGyroscopeWarningDialog() {
229         if (mNoGyroscopeWarningDialog == null) {
230             mNoGyroscopeWarningDialog = new AlertDialog.Builder(GyroscopeTestActivity.this)
231                 .setIcon(android.R.drawable.ic_dialog_alert)
232                 .setTitle(R.string.snsr_gyro_test_no_gyro_title)
233                 .setMessage(R.string.snsr_gyro_test_no_gyro_message)
234                 .setPositiveButton(android.R.string.ok, null)
235                 .create();
236         }
237         if (!mNoGyroscopeWarningDialog.isShowing()) {
238             mNoGyroscopeWarningDialog.show();
239         }
240     }
241 
showDegreesWarningDialog()242     private void showDegreesWarningDialog() {
243         if (mDegreesWarningDialog == null) {
244             mDegreesWarningDialog = new AlertDialog.Builder(GyroscopeTestActivity.this)
245                     .setIcon(android.R.drawable.ic_dialog_alert)
246                     .setTitle(R.string.snsr_gyro_test_degrees_title)
247                     .setMessage(R.string.snsr_gyro_test_degrees_message)
248                     .setPositiveButton(android.R.string.ok, null)
249                     .create();
250         }
251         if (!mDegreesWarningDialog.isShowing()) {
252             mDegreesWarningDialog.show();
253         }
254     }
255 }
256