Detect Android Shake event
Detect Android Shake event
activity_main .xml
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin" android:paddingRight="@dimen/activity_horizontal_margin" android:paddingTop="@dimen/activity_vertical_margin" android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".MainActivity">
<TextView android:text="@string/hello_world" android:layout_width="wrap_content" android:layout_height="wrap_content" />
</RelativeLayout>
shakedetector.java
import android.hardware.Sensor;
import android.hardware.SensorEvent;
import android.hardware.SensorEventListener;
public class ShakeDetector implements SensorEventListener {
// Minimum acceleration needed to count as a shake movement private static final int MIN_SHAKE_ACCELERATION = 5;
// Minimum number of movements to register a shake private static final int MIN_MOVEMENTS = 2;
// Maximum time (in milliseconds) for the whole shake to occur private static final int MAX_SHAKE_DURATION = 500;
// Arrays to store gravity and linear acceleration values private float[] mGravity = { 0.0f, 0.0f, 0.0f };
private float[] mLinearAcceleration = { 0.0f, 0.0f, 0.0f };
// Indexes for x, y, and z values private static final int X = 0;
private static final int Y = 1;
private static final int Z = 2;
// OnShakeListener that will be notified when the shake is detected private OnShakeListener mShakeListener;
// Start time for the shake detection long startTime = 0;
// Counter for shake movements int moveCount = 0;
// Constructor that sets the shake listener public ShakeDetector(OnShakeListener shakeListener) {
mShakeListener = shakeListener;
}
@Override
public void onSensorChanged(SensorEvent event) {
// This method will be called when the accelerometer detects a change.
// Call a helper method that wraps code from the Android developer site setCurrentAcceleration(event);
// Get the max linear acceleration in any direction float maxLinearAcceleration = getMaxCurrentLinearAcceleration();
// Check if the acceleration is greater than our minimum threshold if (maxLinearAcceleration > MIN_SHAKE_ACCELERATION) {
long now = System.currentTimeMillis();
// Set the startTime if it was reset to zero if (startTime == 0) {
startTime = now;
}
long elapsedTime = now - startTime;
// Check if we're still in the shake window we defined if (elapsedTime > MAX_SHAKE_DURATION) {
// Too much time has passed. Start over! resetShakeDetection();
}
else {
// Keep track of all the movements moveCount++;
// Check if enough movements have been made to qualify as a shake if (moveCount > MIN_MOVEMENTS) {
// It's a shake! Notify the listener. mShakeListener.onShake();
// Reset for the next one! resetShakeDetection();
}
}
}
}
@Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
// Intentionally blank }
private void setCurrentAcceleration(SensorEvent event) {
/* * BEGIN SECTION from Android developer site. This code accounts for * gravity using a high-pass filter */
// alpha is calculated as t / (t + dT) // with t, the low-pass filter's time-constant // and dT, the event delivery rate
final float alpha = 0.8f;
// Gravity components of x, y, and z acceleration mGravity[X] = alpha * mGravity[X] + (1 - alpha) * event.values[X];
mGravity[Y] = alpha * mGravity[Y] + (1 - alpha) * event.values[Y];
mGravity[Z] = alpha * mGravity[Z] + (1 - alpha) * event.values[Z];
// Linear acceleration along the x, y, and z axes (gravity effects removed) mLinearAcceleration[X] = event.values[X] - mGravity[X];
mLinearAcceleration[Y] = event.values[Y] - mGravity[Y];
mLinearAcceleration[Z] = event.values[Z] - mGravity[Z];
/* * END SECTION from Android developer site */ }
private float getMaxCurrentLinearAcceleration() {
// Start by setting the value to the x value float maxLinearAcceleration = mLinearAcceleration[X];
// Check if the y value is greater if (mLinearAcceleration[Y] > maxLinearAcceleration) {
maxLinearAcceleration = mLinearAcceleration[Y];
}
// Check if the z value is greater if (mLinearAcceleration[Z] > maxLinearAcceleration) {
maxLinearAcceleration = mLinearAcceleration[Z];
}
// Return the greatest value return maxLinearAcceleration;
}
private void resetShakeDetection() {
startTime = 0;
moveCount = 0;
}
// (I'd normally put this definition in it's own .java file) public interface OnShakeListener {
public void onShake();
}
}
MainActivity.java
import android.app.Activity;
import android.content.Context;
import android.hardware.Sensor;
import android.hardware.SensorManager;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.Toast;
public class MainActivity extends Activity {
private ShakeDetector mShakeDetector;
private SensorManager mSensorManager;
private Sensor mAccelerometer;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// ShakeDetector initialization mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
mAccelerometer = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
mShakeDetector = new ShakeDetector(new ShakeDetector.OnShakeListener() {
@Override
public void onShake() {
// Do stuff! Toast.makeText(MainActivity.this, "Don't shake me, bro!", Toast.LENGTH_SHORT).show();
}
});
}
@Override
protected void onResume() {
super.onResume();
mSensorManager.registerListener(mShakeDetector, mAccelerometer, SensorManager.SENSOR_DELAY_UI);
}
@Override
protected void onPause() {
mSensorManager.unregisterListener(mShakeDetector);
super.onPause();
}
}
I Am Not The Owner Of These Code .I Merely Have Copied Them From Various Sources. The Only Thing I Did Is That I Am Going To Present Them In More Easy Way To Understand.
Comments
Post a Comment