在Android 6.0以下,系统的休眠和唤醒我们可以调用PowerManager.goToSleep()和PowerManager.wakeUp()。
需要的权限:Android.permission.DEVICE_POWER。
但是在Android 6.0之后你会发现调用不到PowerManager.goToSleep()方法,即使你跳到PowerManager这个类下面且找到 goToSleep方法,但在程序中就是报错不能使用。这个时候我们就可以使用第三方应用实现休眠,用DevicePolicyManager的lockNow()即可。
下面我们来看一下具体如何操作。 要让自己的应用实现该屏幕锁定,主要需要用到以下几个类:
该类继承自 BroadcastReceiver 。从源码可以看到,其实就是实现了一个OnReceive方法,该方法中根据不同的Action,执行相应的操作。
比如,如果激活成功,那么Action就是ACTION_DEVICE_ADMIN_ENABLED, 据此调用 onEnabled 方法。
下面我们就来看下如何实现屏幕锁定。
//获取设备管理服务
policyManager = (DevicePolicyManager) getSystemService(Context.DEVICE_POLICY_SERVICE);
//AdminReceiver 继承自 DeviceAdminReceiver
componentName = new ComponentName(this, AdminReceiver.class);
其中: AdminReceiver 类的代码如下:
package com.yfz.broadcast;
import com.yfz.log.Logger;
import android.app.admin.DeviceAdminInfo;
import android.app.admin.DeviceAdminReceiver;
import android.app.admin.DevicePolicyManager;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.pm.ResolveInfo;
import android.os.IBinder;
import android.widget.Toast;
public class AdminReceiver extends DeviceAdminReceiver {
@Override
public DevicePolicyManager getManager(Context context) {
Logger.d("------" + "getManager" + "------");
return super.getManager(context);
}
@Override
public ComponentName getWho(Context context) {
Logger.d("------" + "getWho" + "------");
return super.getWho(context);
}
/**
* 禁用
*/
@Override
public void onDisabled(Context context, Intent intent) {
Logger.d("------" + "onDisabled" + "------");
Toast.makeText(context, "禁用设备管理", Toast.LENGTH_SHORT).show();
super.onDisabled(context, intent);
}
@Override
public CharSequence onDisableRequested(Context context, Intent intent) {
Logger.d("------" + "onDisableRequested" + "------");
return super.onDisableRequested(context, intent);
}
/**
* 激活
*/
@Override
public void onEnabled(Context context, Intent intent) {
Logger.d("------" + "onEnabled" + "------");
Toast.makeText(context, "启动设备管理", Toast.LENGTH_SHORT).show();
super.onEnabled(context, intent);
}
@Override
public void onPasswordChanged(Context context, Intent intent) {
Logger.d("------" + "onPasswordChanged" + "------");
super.onPasswordChanged(context, intent);
}
@Override
public void onPasswordFailed(Context context, Intent intent) {
Logger.d("------" + "onPasswordFailed" + "------");
super.onPasswordFailed(context, intent);
}
@Override
public void onPasswordSucceeded(Context context, Intent intent) {
Logger.d("------" + "onPasswordSucceeded" + "------");
super.onPasswordSucceeded(context, intent);
}
@Override
public void onReceive(Context context, Intent intent) {
Logger.d("------" + "onReceive" + "------");
super.onReceive(context, intent);
}
@Override
public IBinder peekService(Context myContext, Intent service) {
Logger.d("------" + "peekService" + "------");
return super.peekService(myContext, service);
}
}
继承了DeviceAdminReceiver,没有做什么特别操作,仅仅在启动、禁用时输出一个提示消息。
同时,像普通Broadcast类一样,该类也需要在 AndroidManifest.xml 文件中注册。
android:resource="@xml/lock_screen" 对应的就是权限说明文件。
"激活"按钮 执行代码:
/**
* 激活设备管理权限
* 成功执行激活时,DeviceAdminReceiver中的 onEnabled 会响应
*/
private void activeManage() {
// 启动设备管理(隐式Intent) - 在AndroidManifest.xml中设定相应过滤器
Intent intent = new Intent(DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN);
//权限列表
intent.putExtra(DevicePolicyManager.EXTRA_DEVICE_ADMIN, componentName);
//描述(additional explanation)
intent.putExtra(DevicePolicyManager.EXTRA_ADD_EXPLANATION, "------ 其他描述 ------");
startActivityForResult(intent, 0);
}
这边就是用了一个隐式Intent ,通过这个Intent (DevicePolicyManager.ACTION_ADD_DEVICE_ADMIN)跳转到 权限提醒页面。 同时传递了两个参数EXTRA_DEVICE_ADMIN 、 EXTRA_ADD_EXPLANATION。 点击"激活"。
此时该应用就拥有了设备管理权限。 激活时 AdminReceiver 类的 onEnabled方法会被调用。
/**
* 禁用设备管理权限
* 成功执行禁用时,DeviceAdminReceiver中的 onDisabled 会响应
*/
private void unActiveManage() {
Logger.d("------ unActiveManage ------");
boolean active = policyManager.isAdminActive(componentName);
if (active) {
policyManager.removeActiveAdmin(componentName);
}
}
禁用时 AdminReceiver 类的 onDisabled方法会被调用。
boolean active = policyManager.isAdminActive(componentName);
if (active) {
policyManager.lockNow();
}