转自:http://shigongbo.blog.163.com/blog/static/976090201452572535715

今天看到某Android安全软件有一个安全锁的功能,使用的时候,点击返回竟然是无效的,必须要用户输入密码!这用户体验也太差了!在网上查了一下,发现许多人都是在Activity中显示解锁画面,并屏蔽返回键。我感觉这样用户体验很差,于是就想自己实现一个。现在把主要思路和代码分享一下。

其实这个程序核心代码很少,不超过一百行就搞定。不过其中牵扯到的Android知识点很多,现在听我从头道来。
我们先来解释一下APPLock的原理。
用户启动APPLock,此时会列出所有的应用程序,选择要Lock的应用,将此应用的信息(包名)保存到数据库或文件。
并启动一个Service,我们称其为LockService,在后台一直监听,查看要Lock的应用是否被启动。
当用户启动了要Lock的应用,LockService就会察觉到,此时显示密码界面,让用户输入密码,密码正确后,密码界面消失。
如果密码界面正在显示的时候,用户点击返回,会怎么样?那肯定是密码界面消失,要启动的应用显示出来,这就不能达到应用锁的效果,所以开发者选择了在密码界面屏蔽返回键的方式。体验太差!

首先,要解决的就是怎么避免使用Activity显示解锁画面并屏蔽返回键这种不好的用户体验。
既要显示画面,又要不屏蔽返回键,怎么实现呢?
Service!对,就是在Service中显示画面。使用WindowManager加载layout的方式,让解锁画面显示在最前端。

View mLockView;
TextView mTextView;
WindowManager mWindowManager = null;mContext = getApplicationContext();WindowManager.LayoutParams params = new WindowManager.LayoutParams(
                WindowManager.LayoutParams.MATCH_PARENT,
                WindowManager.LayoutParams.MATCH_PARENT,
                WindowManager.LayoutParams.TYPE_SYSTEM_OVERLAY,
                WindowManager.LayoutParams.FLAG_FULLSCREEN |
                        WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
                PixelFormat.RGBA_8888);
        params.gravity = (Gravity.CENTER);        mLockView= layoutInflater.inflate(R.layout.lock_app_service, null);
        mTextView = (TextView) mLockView.findViewById(R.id.service_input_pwd);        if (mWindowManager == null) {            mWindowManager = (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
        }        if (mWindowManager != null && mLockView!= null) {            mWindowManager.addView(mLockView, params);
        }

把这段加到LockService中,它会显示一个覆盖屏幕的画面,也就是你xml定义的文件lock_app_service。
要使用这个功能,你还要在Manifest中添加权限

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

这样这个画面运行的时候就会在最前端覆盖整个屏幕了。
正式因为这是用WindowManager在最前端画出的,所以当前运行的Activity并不受影响,还是在正常运行,并不会改变生命周期,你可以在onPause中打印Log来印证,你会发现onPause并不会调用。

现在再看看怎么检测要Lock的应用开始启动了。Android中启动一个Activity的时候并没有对应的广播事件。启动一个Activity,首先是发送Intent,ActivityManagerService(AMS)会处理这个Intent。首先AMS会检测这个要启动的Activity是否存在,然后判断判断启动者是否有权限启动被启动的Activity(根据 PID和UID ),然后把被启动的Activity压入栈中。
我们就是根据这一特点,来判断刚刚启动的Activity是否为被Lock的。

ActivityManager mActivityManager;mActivityManager = (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE);
ComponentName topActivity = mActivityManager.getRunningTasks(1).get(0).topActivity;
String packageName = topActivity.getPackageName();
String className = topActivity.getClassName();
Log.v("LockService", "packageName == " + packageName);
Log.v("LockService", "className == " + className);

从Log信息可以发现,此时出现的肯定是当前正在运行的应用的包名和Activity名字。
要运行这个功能,需要添加权限

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

OK,核心功能就只有这么几行,是不是不超过一百行!

剩下的工作就是界面配置和Service启动方面的了。我在这里只说一下思路。
1. 启动LockActivity。
这是一个含有list的界面,外加一个Lock开关按钮。当开关On状态,启动LockService。Off状态关闭LockService。
list中列出所有的APP应用。获取已经安装应用,代码如下

        List<PackageInfo> packages = getPackageManager().getInstalledPackages(0);
        for(int i=0;i<packages.size();i++) {            PackageInfo packageInfo = packages.get(i);
            Log.v("LockActivity", "packageInfo.packageName == " + packageInfo.packageName);
            Log.v("LockActivity", "packageInfo.versionName == " + packageInfo.versionName);
            Log.v("LockActivity", "packageInfo.versionCode == " + packageInfo.versionCode);
        }

当用户点击list中的Item时候,将该应用的信息保存到数据库或者文件中。
2. LockService运行后,在其中写一个线程,不停地循环判断Activity栈顶是不是要Lock的Activity。
是,则显示密码界面,并保存当前状态。否则continue。
当用户输入了正确的密码,这则消失掉界面,代码为

mWindowManager.removeView(mLockView);

这样就显示了真正的Activity了。
当用户点击了返回,由于我们的LockService中的WindowManager并没有改变实际的启动Activity的生命周期,所以返回键还是作用在实际Activity上了,所以实际Activity消失,此时根据后台的循环判断,最上次的Activity栈已经不是要被Lock的,根据刚才保存的状态,同样将密码界面消失掉。

OK。大功告成。整个应用程序安全管家就完成了。

Android 应用锁/程序锁(APPLock)的实现 http://shigongbo.blog.163.com/blog/static/976090201452572535715相关推荐

  1. 85程序锁的工作原理

    程序锁实际上就是一个看门狗的服务,在一个死循环中不停的检查系统程序的运行信息. 这里在设置界面新增一个开启开门狗的控件: <com.ustc.mobilemanager.ui.SettingIt ...

  2. Bug:正试图在 OS 加载程序锁内执行托管代码

    在运行程序退出后,有时候会不然出现这样的错误:正试图在 os 加载程序锁内执行托管代码.不要尝试在DllMain 或映像初始化函数内运行托管代码,这样做会导致应用程序挂起. 解决方法是: 把vs200 ...

  3. android判断是否已经安装成功,android 判断应用程序是否已安装

    1.判断是否安装 /* * check the app is installed */ private boolean isAppInstalled(Context context,String pa ...

  4. 适用于Android设备的十大应用程序锁

    现如今的智能手机非常个人化,其中的应用程序确实会携带不同形式的个人数据,例如图片,消息,银行应用程序等. 应用锁也称为隐私锁,它是所有移动用户最关注的隐私问题之一.可以保护应用程序免受陌生人或在智能手 ...

  5. android安全问题(二) 程序锁

    导读:本文介绍如何实现对应用加锁的功能,无须root权限 某些人有时候会有这样一种需求,小A下载了个软件,只是软件中的美女过于诱惑与暴露,所以他不想让别人知道这是个什么软件,起码不想让别人打开浏览.而 ...

  6. Android 解锁app,应用锁「AppLock」v3.3.0 for Android 完美解锁版

    摘要 一款可以有效保护您应用.图片.视频等隐私的应用 随着我们的手机越来越智能,我们的隐私也同样一一的都储存在了里面,于是隐私安全就成为了重中之重的大事.恩!您可以考虑试试今天这款应用锁「AppLoc ...

  7. Android开发——程序锁的实现(可用于开发钓鱼登录界面)

    1. 程序锁原理 1.1 实现效果: 在用户打开一个应用时,若此应用是我们业务内的逻辑拦截目标,那就在开启应用之后,弹出一个输入密码的界面,输入密码正确则进入目标应用.若不输入直接按返回键,则直接返回 ...

  8. Android程序锁的实现

    1.程序功能介绍 本程序实现对特定应用的监听,当特定应用前台运行时,立刻弹出本程序锁应用界面,用户输入正确密码后,才能转到特定应用继续使用,用户点击后退按钮无效,点击home键后,再启动被锁应用后,仍 ...

  9. android程序锁预研

    项目要求增加程序锁功能.要预研一下. 网上反编了比较流行的程序锁,了解到大概方向: 1 后台服务不断监视显示在前台的应用. 2 当是需要锁住的应用,启动程序锁密码页面. 3 密码成功则关闭程序锁密码页 ...

最新文章

  1. 并查集-----好忧伤的并查集
  2. 451 Sort Characters By Frequency
  3. android eng 模式,android 4.0 编译模式 eng - user 时遇到的有关问题
  4. 数据结构-----红黑树的插入操作
  5. Python pandas模块输出每行中间省略号问题
  6. 在word中,整篇文章想要在每一章另起一页
  7. (软件工程复习核心重点)第二章可行性研究-第三节:数据流图
  8. java编写母亲节快乐_写在母亲节来临之际
  9. 设计师常用网页小图标大全
  10. TCP 理论概述与 Java 编码入门
  11. python求幂集_求幂集的算法 - Sethylar的个人页面 - OSCHINA - 中文开源技术交流社区...
  12. 论文阅读:SCENE TRANSFORMER: A UNIFIED ARCHITECTUREFOR PREDICTING MULTIPLE AGENT TRAJECTORIES
  13. win8系统 ps不能直接拖入图片的问题!解决方法
  14. 分布式存储大行其道 浪潮AS13000何以“木秀于林”?
  15. codeforces 596E Wilbur and Strings
  16. 虚拟现实技术利用计算机,虚拟现实 虚拟现实技术是一种可以创建和体验虚拟世界的计算机仿真系统它利用计算机生...
  17. NLP - 文本向量化
  18. 计算机公共课5——演示文稿软件 PowerPoint 2010
  19. 关于食物消化,避免损害和改善肠道健康的建议(科学支持)
  20. 定期把电脑的文件备份到服务器,怎么让电脑定期自动备份文件或文件夹(学会这一招,让电脑自动备份你的重要资料)...

热门文章

  1. Share:电脑右下角 今日热文 广告和图标怎么关闭
  2. 高斯列主元消去法——C实现
  3. Caff-Opencv——图像分类(01)
  4. 十大最佳DevOps工具
  5. 股票市场市价委托类型
  6. 原型图高保真和中保真的区别_具有自适应性能的更高保真度和更平滑的帧频
  7. 32.768K晶振通过CD4060分频后频率过高
  8. [Previous line repeated 995 more times]RecursionError: maximum recursion depth exceeded
  9. 如何设置app字体跟随系统_Android 应用全局字体调节或禁止随系统字体大小更改...
  10. android应用程序如何获取root权限,Android获取ROOT权限的实例代码