Back to project page Resonos-Android-Framework.
The source code is released under:
Apache License
If you think the Android project Resonos-Android-Framework listed in this page is inappropriate, such as containing malicious code/tools or violating the copyright, please email info at java2s dot com, thanks.
package com.resonos.apps.library.util; //from w ww .ja v a 2 s . c o m import android.app.Activity; import android.content.Context; import android.content.pm.ActivityInfo; import android.hardware.Sensor; import android.hardware.SensorEvent; import android.hardware.SensorEventListener; import android.hardware.SensorManager; import android.util.DisplayMetrics; import android.view.Surface; import android.view.WindowManager; /** * A thread-safe class for accessing accelerometer and magnetic field data * (and therefore orientation data as well. Based on some code from LibGDX. */ public class SensorReader implements SensorEventListener { // context private final Activity cx; // objects private SensorManager manager; // vars private boolean bAccelerometerAvailable = false; private boolean bCompassAvailable = false; private boolean bDirty = true; private final float[] mDataAccelerometerValues = new float[3]; private final float[] mDataMagneticFieldValues = new float[3]; private final float[] mDataRotationMatrix = new float[9]; private final float[] mDataOrientation = new float[3]; private float mDataAzimuth = 0; private float mDataPitch = 0; private float mDataRoll = 0; private Orientation mNativeOrientation; // enums private enum Orientation {PORTRAIT, LANDSCAPE}; /** * Construct the Sensor reader using a context object. * @param context */ public SensorReader(Activity cx) { this.cx = cx; } /** * @return true if both the accelerometer and magnetic field sensor are available. */ public boolean sensorsAvailable() { mNativeOrientation = getNativeOrientation(); manager = (SensorManager) cx.getSystemService(Context.SENSOR_SERVICE); bAccelerometerAvailable = (manager.getSensorList( Sensor.TYPE_ACCELEROMETER).size() > 0); bCompassAvailable = (manager.getSensorList(Sensor.TYPE_MAGNETIC_FIELD) .size() > 0); return bAccelerometerAvailable && bCompassAvailable; } /** * Start listening to sensor data. */ public void registerSensorListeners() { unregisterSensorListeners(); cx.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_NOSENSOR); manager = (SensorManager) cx.getSystemService(Context.SENSOR_SERVICE); if (manager.getSensorList(Sensor.TYPE_ACCELEROMETER).size() == 0) { bAccelerometerAvailable = false; } else { Sensor accelerometer = manager.getSensorList( Sensor.TYPE_ACCELEROMETER).get(0); bAccelerometerAvailable = manager.registerListener(this, accelerometer, SensorManager.SENSOR_DELAY_GAME); } if (manager == null) manager = (SensorManager) cx .getSystemService(Context.SENSOR_SERVICE); Sensor sensor = manager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD); if (sensor != null) { bCompassAvailable = bAccelerometerAvailable; if (bCompassAvailable) { bCompassAvailable = manager.registerListener(this, sensor, SensorManager.SENSOR_DELAY_GAME); } } else { bCompassAvailable = false; } } /** * Stop listening to sensor data. Safe to call unlimited times. */ public void unregisterSensorListeners() { if (manager != null) { cx.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED); manager.unregisterListener(this); manager = null; } } /** * @return Accelerometer X value */ public float getAccelerometerX() { return mDataAccelerometerValues[0]; } /** * @return Accelerometer Y value */ public float getAccelerometerY() { return mDataAccelerometerValues[1]; } /** * @return Accelerometer Z value */ public float getAccelerometerZ() { return mDataAccelerometerValues[2]; } @Override public synchronized void onSensorChanged(SensorEvent event) { if (event.sensor.getType() == Sensor.TYPE_ACCELEROMETER) { if (mNativeOrientation == Orientation.PORTRAIT) { System.arraycopy(event.values, 0, mDataAccelerometerValues, 0, mDataAccelerometerValues.length); } else { mDataAccelerometerValues[0] = event.values[1]; mDataAccelerometerValues[1] = -event.values[0]; mDataAccelerometerValues[2] = event.values[2]; } bDirty = true; } if (event.sensor.getType() == Sensor.TYPE_MAGNETIC_FIELD) { System.arraycopy(event.values, 0, mDataMagneticFieldValues, 0, mDataMagneticFieldValues.length); bDirty = true; } } /** * Calculate and update internal orientation data, iff the data is dirty */ private synchronized void updateOrientation() { if (!bDirty) return; if (SensorManager.getRotationMatrix(mDataRotationMatrix, null, mDataAccelerometerValues, mDataMagneticFieldValues)) { SensorManager.getOrientation(mDataRotationMatrix, mDataOrientation); synchronized (this) { mDataAzimuth = (float) Math.toDegrees(mDataOrientation[0]); mDataPitch = (float) Math.toDegrees(mDataOrientation[1]); mDataRoll = (float) Math.toDegrees(mDataOrientation[2]); } } bDirty = false; } /** * @return Orientation Azimuth */ public synchronized float getAzimuth() { if (!bCompassAvailable) return 0; updateOrientation(); return mDataAzimuth; } /** * @return Orientation Pitch */ public synchronized float getPitch() { if (!bCompassAvailable) return 0; updateOrientation(); return mDataPitch; } /** * @return Orientation Roll */ public synchronized float getRoll() { if (!bCompassAvailable) return 0; updateOrientation(); return mDataRoll; } /** * @return The angle in degrees representing screen rotation. * Either 0, 90, 180, or 270. */ private int getRotation() { WindowManager wm = (WindowManager) cx .getSystemService(Context.WINDOW_SERVICE); int rotation = wm.getDefaultDisplay().getRotation(); switch (rotation) { case Surface.ROTATION_0: return 0; case Surface.ROTATION_90: return 90; case Surface.ROTATION_180: return 180; case Surface.ROTATION_270: return 270; default: return 0; } } /** * @return The native orientation of the device */ private Orientation getNativeOrientation() { int rotation = getRotation(); DisplayMetrics metrics = new DisplayMetrics(); WindowManager wm = (WindowManager) cx .getSystemService(Context.WINDOW_SERVICE); wm.getDefaultDisplay().getMetrics(metrics); if (((rotation == 0 || rotation == 180) && (metrics.widthPixels >= metrics.heightPixels)) || ((rotation == 90 || rotation == 270) && (metrics.widthPixels <= metrics.heightPixels))) { return Orientation.LANDSCAPE; } else { return Orientation.PORTRAIT; } } @Override public void onAccuracyChanged(Sensor arg0, int arg1) { // unused } }