【问题标题】:Android Sensor Shake in the backgroundAndroid Sensor Shake 在后台
【发布时间】:2016-08-10 19:50:15
【问题描述】:

我正在尝试学习有关传感器的教程。它适用于活动。但是,我希望它在手机锁定时在后台工作。最好的方法是什么?

这是教程的链接 http://jasonmcreynolds.com/?p=388

ShakeDetector 类

public class ShakeDetector implements SensorEventListener {

/*
 * The gForce that is necessary to register as shake.
 * Must be greater than 1G (one earth gravity unit).
 * You can install "G-Force", by Blake La Pierre
 * from the Google Play Store and run it to see how
 *  many G's it takes to register a shake
 */
private static final float SHAKE_THRESHOLD_GRAVITY = 2.7F;
private static final int SHAKE_SLOP_TIME_MS = 500;
private static final int SHAKE_COUNT_RESET_TIME_MS = 3000;

private OnShakeListener mListener;
private long mShakeTimestamp;
private int mShakeCount;

public void setOnShakeListener(OnShakeListener listener) {
    this.mListener = listener;
}

public interface OnShakeListener {
    public void onShake(int count);
}

@Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
    // ignore
}

@Override
public void onSensorChanged(SensorEvent event) {

    if (mListener != null) {
        float x = event.values[0];
        float y = event.values[1];
        float z = event.values[2];

        float gX = x / SensorManager.GRAVITY_EARTH;
        float gY = y / SensorManager.GRAVITY_EARTH;
        float gZ = z / SensorManager.GRAVITY_EARTH;

        // gForce will be close to 1 when there is no movement.
        Float f = new Float(gX * gX + gY * gY + gZ * gZ);
        Double d = Math.sqrt(f.doubleValue());
        float gForce = d.floatValue();

        if (gForce > SHAKE_THRESHOLD_GRAVITY) {
            final long now = System.currentTimeMillis();
            // ignore shake events too close to each other (500ms)
            if (mShakeTimestamp + SHAKE_SLOP_TIME_MS > now) {
                return;
            }

            // reset the shake count after 3 seconds of no shakes
            if (mShakeTimestamp + SHAKE_COUNT_RESET_TIME_MS < now) {
                mShakeCount = 0;
            }

            mShakeTimestamp = now;
            mShakeCount++;

            mListener.onShake(mShakeCount);
        }
    }
}
}

主要活动

 public class MainActivity extends AppCompatActivity {

// The following are used for the shake detection
private SensorManager mSensorManager;
private Sensor mAccelerometer;
private ShakeDetector mShakeDetector;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    Intent intent = new Intent(MainActivity.this, ShakeService.class);
    startService(intent);

    // ShakeDetector initialization
    mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
    mAccelerometer = mSensorManager
            .getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
    mShakeDetector = new ShakeDetector();
    mShakeDetector.setOnShakeListener(new ShakeDetector.OnShakeListener() {

        @Override
        public void onShake(int count) {
            Toast.makeText(getApplicationContext(), "shake",Toast.LENGTH_SHORT).show();
        }
    });
}

@Override
public void onResume() {
    super.onResume();
    // Add the following line to register the Session Manager Listener onResume
    mSensorManager.registerListener(mShakeDetector, mAccelerometer, SensorManager.SENSOR_DELAY_UI);
}

@Override
public void onPause() {
    // Add the following line to unregister the Sensor Manager onPause
    mSensorManager.unregisterListener(mShakeDetector);
    super.onPause();
}

}

摇一摇服务

public class ShakeService extends Service {

private SensorManager mSensorManager;
private Sensor mAccelerometer;
private ShakeDetector mShakeDetector;

public ShakeService() {
}

@Override
public IBinder onBind(Intent intent) {
    // TODO: Return the communication channel to the service.
    throw new UnsupportedOperationException("Not yet implemented");
}

@Override
public void onCreate() {
    super.onCreate();
    // ShakeDetector initialization
    mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
    mAccelerometer = mSensorManager
            .getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
    mShakeDetector = new ShakeDetector();
    mShakeDetector.setOnShakeListener(new ShakeDetector.OnShakeListener() {

        @Override
        public void onShake(int count) {

            Intent i = getApplicationContext().getPackageManager().getLaunchIntentForPackage("com.facebook.katana");
            getApplicationContext().startActivity(i);

        }
    });
    mSensorManager.registerListener(mShakeDetector, mAccelerometer, SensorManager.SENSOR_DELAY_UI);
}

@Override
public void onDestroy() {
    mSensorManager.unregisterListener(mShakeDetector);
    super.onDestroy();
}

}

【问题讨论】:

  • 您的服务有什么问题?你有错误吗?
  • 确实有效。但是,即使我的手机被锁定,我也希望它能够正常工作。
  • 当您的手机被锁定时,服务实际上正在运行,但是当您摇动手机时,活动不会启动,因为屏幕已关闭。在this question 获得战利品,找到在屏幕关闭时启动活动的方法。
  • 我不需要在屏幕锁定时启动活动。我需要服务在手机震动时调用服务中的方法。
  • 那么,它不是在调用方法吗?

标签: android android-service android-sensors android-service-binding


【解决方案1】:

你需要使用线程,AsyncTask 是最容易实现的。看看这个,如果这就是你要找的东西:https://developer.android.com/guide/components/processes-and-threads.html

【讨论】:

    【解决方案2】:

    这是一个谷歌示例 http://joerichard.net/android/android-shake-detector/

    步骤:创建一个传感器事件监听器,然后从Activity中获取。创建一个在抖动事件发生时触发的服务。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-12-08
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多