跳转至

Android 当靠近手机时熄屏,远离手机时恢复亮屏

更新日期 2024-10-25
  • 2024-10-25 增加sensorManager.flush
  • 2024-10-23 新建文档

在一些通话场景中,如果用户将手机贴近耳朵,此时熄屏避免用户误触。通话结束或者手机放下时,恢复屏幕显示。 模仿手机通话的功能逻辑。

测试手机

  • Redmi 9A - MIUI12.5.21 - Android 11
  • HUAWEI nova 3i - HarmonyOS 2.0.0
  • iQOO Neo8 - Android 14

在activity中获取距离传感器信息,判断手机是否贴近物体。 靠近,则息屏。远离则恢复。如果离开界面也恢复。

申请权限

<uses-permission android:name="android.permission.WAKE_LOCK"/>

Activiy代码

import android.hardware.Sensor;
import android.hardware.SensorEvent;
import android.hardware.SensorEventListener;
import android.hardware.SensorManager;
import android.os.Build;
import android.os.Bundle;
import android.os.PowerManager;
import android.text.TextUtils;
import android.view.View;
import android.view.WindowManager;
import android.widget.Toast;

import androidx.annotation.Nullable;

public class RustFisherDemoActivity implements SensorEventListener {

    private SensorManager sensorManager;
    private Sensor proximitySensor;
    private PowerManager powerManager;
    private PowerManager.WakeLock wakeLock;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        // 此处忽略设置layout

        sensorManager = (SensorManager) getSystemService(SENSOR_SERVICE);
        proximitySensor = sensorManager.getDefaultSensor(Sensor.TYPE_PROXIMITY);
        powerManager = (PowerManager) getSystemService(POWER_SERVICE);

        getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);

        // 其他业务代码 ...
    }

    @Override
    protected void onResume() {
        super.onResume();
        sensorManager.registerListener(this, proximitySensor, 500000);
    }

    @Override
    protected void onPause() {
        super.onPause();
        sensorManager.unregisterListener(this);
        sensorManager.flush(sensorEventListener);
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();

        releaseWakeLock();
    }

    private void acquireWakeLock() {
        // "息屏"
        if (wakeLock == null) {
            wakeLock = powerManager.newWakeLock(PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK, "RustFisherDemo:PageWakeLock");
        }
        wakeLock.acquire();
    }

    private void releaseWakeLock() {
        if (wakeLock != null && wakeLock.isHeld()) {
            // 不息屏
            wakeLock.release();
        }

    }

    @Override
    public void onSensorChanged(SensorEvent event) {
        if (event.sensor.getType() == Sensor.TYPE_PROXIMITY) {
            // "event.values[0]: " + event.values[0] + " , max range:" + proximitySensor.getMaximumRange()
            if (event.values[0] < proximitySensor.getMaximumRange()) {
                // 设备接近物体,息屏
                acquireWakeLock();
            } else {
                // 设备远离物体,亮屏
                releaseWakeLock();
            }
        }
    }

    @Override
    public void onAccuracyChanged(Sensor sensor, int accuracy) {
        // 传感器精度变化时的处理,通常不需要特别处理
    }
}

熄屏和恢复主要使用PowerManager获取PowerManager.WakeLock

注意熄屏要使用 PowerManager.PROXIMITY_SCREEN_OFF_WAKE_LOCK

某些华为、荣耀手机需要 sensorManager.flush(sensorEventListener); 。否则离开界面后,应用还是会走熄屏逻辑。

本站说明

一起在知识的海洋里呛水吧。广告内容与本站无关。如果喜欢本站内容,欢迎投喂作者,谢谢支持服务器。如有疑问和建议,欢迎在下方评论~

📖AndroidTutorial 📚AndroidTutorial 🙋反馈问题 🔥最近更新 🍪投喂作者

Ads