我要当学霸这款App有个学习监督的功能,当你启动它的时候,你将无法使用其他App,以此达到帮助人提高自觉性,起到监督学习的效果。最近和同学做了个小App,正好有这个功能,所以就来说说它是怎么实现的。

PS:本篇描述的是我们做这个小App过程中的一些尝试。


效果

首先还是先来看下效果是怎么样的:
  

实现思路

  先说下我们这个小App的功能:学习监督的功能(即禁掉其他App的使用) + 桌面小宠物(用来给用户提示的)。
  从上图也可以看出,当启动我们这个小App时,开启监督功能后,再点击其他App(如QQ)的时候,桌面小宠物是会给出一些温馨提示的,然后再把刚才你打开的App关闭掉。

那么它是怎么实现呢?首先我们肯定需要监测到用户打开了什么App,那这点怎么实现呢?

1. getRunningTasks()

  最开始想到的是能否用Activity堆栈,也就是ActivityManager里的一个getRunningTasks()方法,调用这个方法也就可以获取当前正在运行中的任务栈,而处于栈顶的也就是我们在这个时刻打开的App。我们只要不断地读取这个任务栈,也就能达到了监测用户打开App的功能了,完美解决。
  但很遗憾,使用的时候才发现这个方法已经被抛弃了。我们看下源代码里怎么说的:

也就是说在安卓5.0以上的机器,这个方法已经不再为第三方应用使用的了。所以只能另想办法了。

2. getRunningAppProcesses()

  接下去没思路了,就到网上随便搜一些关键词,出来了很多博客,有说用getRunningAppProcesses(),先看下这个方法的介绍:

  返回正在运行中的应用进程集合,然后再通过进程找到对应的包名就可以了。可是返回的集合序列并没有什么特定的排序方式,也就是随机的,那么我们该怎么判断哪个进程才是刚打开的App创建的呢?
  要么可以先指定一些应用程序,只要判断返回的集合里有我们指定的应用程序,那么就可以判断是打开了那个应用。
  要么可以比较上一时刻返回的集合和这一时刻返回的集合,对比看多了哪些进程,少了哪些进程也就可以判断出打开或关闭了某个应用。
  好,实现的思路大概有了,接下去可以敲代码了。当敲完在真机上测试时,发现不管怎么样返回的都只有该应用的信息。
  网上搜了下,发现这个方法权限又被官方弱化了:

  我测试用的真机是5.0.+的安卓系统,网上也有解释说有的手机厂家在5.0版本上就已经弱化了getRunningAppProcesses的权限,难怪只会返回应用本身的信息。可这样一来就又跟第一个思路一样了,这个方法也不能采用了。

3. Linux系统内核会把process进程信息保存在/proc目录下

  上面两种思路都不行,只能再找思路了,后来在stackoverflow中,无意间搜到了国外一牛人的解决方法,他是利用Linux系统的漏洞,Linux系统内核会把process进程信息保存在/proc目录下,只要读取到进程信息,就可以根据进程的属性来判断是否是前台进程了。这个牛人还把它封装成了个开源项目,附上Github地址:https://github.com/jaredrummler/AndroidProcesses
  这样一来就可以获取到所有的进程信息,但就算拿到所有进程信息又要怎么通过进程判断出用户打开了哪个App呢?
  进程有个属性可以用来区分它是前台进程还是后台进程,关于这两者的区别我不是很理解,但我猜想,是否可以将前台进程类比成正在运行中的进程?如果可以这样,那么再利用第2个思路中提到的方案,就可以实现监测用户打开App的功能了。
  于是,我便去尝试一下。后来真机测试时,发现当打开大多数应用时都可以达到预期的效果。但是有个别应用无论用户打开与否,总能被检测到是处于前台进程中,后来在网上发现有人这么解释:

在聊天类型的App中,常常需要常驻后台来不间断的获取服务器的消息,这就需要我们把Service设置成START_STICKY,kill 后会被重启(等待5秒左右)来保证Service常驻后台。如果Service设置了这个属性,这个App的进程就会被判断是前台,代码上的表现就是appProcess.importance的值永远是 ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND,这样就永远无法判断出到底哪个是前台了。

  于是,这个思路也只能放一边了。

4. 某大神总结

  尝试了各种方法,始终达不到想要的效果。一次偶然情况下,在Github搜到了完美的解决方案,先附上Github地址:https://github.com/wenmingvs/AndroidProcess

  你可以看到这个大神,对监测运行中的进程进行了非常详细的讲解,而且列举了目前能实现的各种方法,也分别介绍了各自的优缺点。
  得益于这个大神的分享,我把它的项目clone下来学习,最后选择了方法五:通过Android无障碍功能实现
  至此,监测用户打开App的功能终于可以实现,有点不足的是每次使用需要用户自己授权,可能会引起用户反感,但想想也是,这种涉及安全性问题的,如果不通过用户自行授权,就好像有点恶意软件的嫌疑了,hhh。

(小小吐槽:早知道有这么个大神给出了这么详细的介绍,我就不用自己花那么多时间去各种尝试了。哭丧脸)

  好了,监测用户打开App的功能解决了,那么剩下的就是实现桌面宠物了。这个挺简单的,也就是悬浮窗,只是在布局文件里换成动图而已,而要实现动图,这里是使用的也是一个开源项目:android-gif-drawable
  之后只需要当监测到用户打开App时,发送广播通知我们的App,做出一些相应的动作,比如桌面宠物给出温馨提示、关闭用户打开的App等等。


【Android】做一款类似我要当学霸里的学习监督的APP的更多相关文章

  1. 个人开发者做一款Android App需要知道的事情

    个人开发者做一款Android App需要知道的事情 在大学时, 自己是学计算机专业的,而且还和老师一起做过一年半的项目. 有时候是不是有这样的想法,做一个自己的网站.但一直未付诸行动.2012年时, ...

  2. 一款类似塔防类的保卫羊村游戏android源码

    一款类似塔防类的保卫羊村游戏源码,这个游戏很像我们平时玩的塔防游戏的,游戏的源码比较完整的,大家可以修改一下或者添加一些广告就可以上线到应用商店了,而且这个游戏目前已经上线国内的一些应用商店了,360 ...

  3. 如何做一款自己的Android App

    转自:http://www.cnblogs.com/hubcarl/p/4030884.html 正在做App,后续补充: 概述:以我开发的一款编程学习的App[编程在线]为例讲讲如何做一款自己的An ...

  4. 【转】【51CTO 网+】怎样做一款让用户来电的产品

    [51CTO 网+]怎样做一款让用户来电的产品 据相关调查显示,目前全球移动用户平均每人安装应用约95个,每天使用的应用约35个.可见面对众多的移动应用,用户拥有非常大的选择空间.如果由于交互设计欠佳 ...

  5. fir.im Weekly - 如果让你重新做一款APP

    设想下:如果让你重新做一款 APP ,你会用到哪些开发.设计等资源和工具? 本期的 Weekly 为大家分享了最近不错的 APP 开发资源,大部分是关于 iOS 开发. Android 开发.UI设计 ...

  6. 【译】Design For Maturing Android-为日渐成熟的Android做设计

    为日渐成熟的Android做设计 [声明] 本篇博文英文版原文来自Smashing Magazine,本人经Smashing Magazine邮件授权后翻译,转载请注明出处.谢谢!原文地址. 我将不定 ...

  7. 如何在IDEA里给大数据项目导入该项目的相关源码(博主推荐)(类似eclipse里同一个workspace下单个子项目存在)(图文详解)

    不多说,直接上干货! 如果在一个界面里,可以是单个项目 注意:本文是以gradle项目的方式来做的! 如何在IDEA里正确导入从Github上下载的Gradle项目(含相关源码)(博主推荐)(图文详解 ...

  8. Android 4.3实现类似iOS在音乐播放过程中如果有来电则音乐声音渐小铃声渐大的效果

    目前Android的实现是:有来电时,音乐声音直接停止,铃声直接直接使用设置的铃声音量进行铃声播放. Android 4.3实现类似iOS在音乐播放过程中如果有来电则音乐声音渐小铃声渐大的效果. 如果 ...

  9. 【适合公司业务】全网最详细的IDEA里如何正确新建【普通或者Maven】的Java web项目并发布到Tomcat上运行成功【博主强烈推荐】(类似eclipse里同一个workspace下【多个子项目】并存)(图文详解)

    不多说,直接上干货! 首先,大家要明确,IDEA.Eclipse和MyEclipse等编辑器之间的新建和运行手法是不一样的. 如果是在Myeclipse里,则是File -> new -> ...

随机推荐

  1. OWIN的理解和实践(三) –Middleware开发入门

    上篇我们谈了Host和Server的建立,但Host和Server无法产出任何有实际意义的内容,真正的内容来自于加载于Server的Middleware,本篇我们就着重介绍下Middleware的开发 ...

  2. select * from table 时间长

    优化中发现一个存储过程执行20秒通过profiler 抓取发现时间主要消耗在一个select * from 表,那么问题来了select几万数据竟然花了将近20秒? 问题排查清了程序前端使用了data ...

  3. Async Console Programs 异步控制台程序

    如果你正在写一个控制台程序,你可能最终想要一个异步的main方法,像这样: class Program { static async void Main(string[] args) { ... } ...

  4. js数组转json

    function arrayToJson(o) { var r = []; if (typeof o == "string") return "\"" ...

  5. 更改Photoshop 语言为英语(无需语言包)

    因为有时看国外教程时,手头上的PS是中文的而教程里的界面是英文的,而且中英菜单顺序在某些地方是不一样的,所以很不方便. 终于找到一个非常完美的方法可以把界面换成英文,而且不需任何语言包. 并且试了在最 ...

  6. node.js调试

    用了几天node.js感觉很新奇,但是调试问题实在是愁煞人,开始的时候懒的学习调试方法,看看异常内容就可以了,但随着代码复杂程度的上升,并不是所有错误都是语法错误了,不调试搞不定了,只好搜搜资料,学习 ...

  7. Linux网络编程系列-TCP传输控制

    滑动窗口(sliding window) 滑动窗口是用于流量控制的,发送端根据接收端的处理能力发送数据,不至于造成过多的丢包. 是发送方和接收方间的协调,对方的接收窗口大小就是自己的发送窗口大小. 在 ...

  8. (转)Hibernate事务管理

    Hibernate的事务管理 事务(Transaction)是工作中的基本逻辑单位,可以用于确保数据库能够被正确修改,避免数据只修改了一部分而导致数据不完整,或者在修改时受到用户干扰.作为一名软件设计 ...

  9. Java程序员的日常 —— 多进程开发IO阻塞问题

    本篇仍旧是源于最近的工作,总结一下纪念那些年埋下的坑... 背景故事 需求:"使用进程方式启动另一个程序!" 开发:"OK! Runtime.getRuntime().e ...

  10. SSM 三大框架整合

    上一篇已经讲了整个各个子模块的创建过程以及它们之间的依存关系, 那么这一篇就来正式的整合三大框架(SSM)了. 1, 准备环境1.1 为每个War包工程创建一个Server 那么 添加了Server后 ...