写了一个不太成功的“流氓”app~

前言

昨天闲来无事想试试语音识别,本来想用讯飞的SDK的,但是我用百度搜索的,百度sdk第一条,我就偷个懒用了百度的SDK,实现起来果然很懒。然后突发奇想反正是个demo,不如恶搞一下,弄成只有念出特定的话才能退出APP。本来认为重点是看百度语音识别SDK文档,结果实际上手才发现不给用户退出才是大坑。Android早几年的版本十分容易实现,然而8.0之后权限管理十分严格,各大厂商客制化的时候变得更加严格,流氓软件可太难了。 上都说android多不安全什么的,都是扯淡,所有恶意app的行为都是用户授权的。下面总结一下我的思路。

1. 如何恶意阻止用户退出APP

1.1退出APP的方法

首先我们来总结一下正常状态下用户如何退出一个app

  1. 按返回键。
  2. 按Home键盘。
  3. 下拉状态栏长安功能图标跳转到设置界面,比如Wifi开关按钮。
  4. 按菜单键进入任务视图,切换到别的后台进程或者杀进程清内存。
  5. 通过AI助手唤醒别的APP界面,比如小爱同学,华为小易。
  6. 重启手机

1.2对应防止退出的方法

  1. 对于按返回键的情况,这是最简单的。屏蔽back键就可以了。

重写Activity的onBackPressed(),把super删掉即可。
我使用的是onKeyDown()去屏蔽back键

注意你看到了KeyEvent中有HOME按键。我很负责任的告诉你,这玩意骗人的,低版本的时候可能对应HOME键,但是Android系统早就把这个键取消了,我之前做Android TV的时候就发现了这个问题,即使是TV遥控器上的HOME键,你按下去的时候也不是一个OnKey事件,而是一个广播。Google早就想到如果是onKey事件会被恶意拦截,导致Home键失效用户无法退出。

所以对于HOME键,我是这样处理的:

Android 8.0之后大部分系统广播都不允许静态注册,当时拿到Android O的beta版本时候 了一大堆问题出来,都是因为之前的广播失效。所以我们这里只能使用动态注册,而且动态注册的优先级比较高嘛。当我们的APP知道HOME键被触发的时候,重新打开Activity。注意要使用Intent.FLAG_ACTIVITY_NEW_TASK,否则会创建新的实例,我的Activity launchMode设置的也是singleTask。

实际测试中发现会有一些问题,如果使用全面屏手势的方法进入HOME,动画没有执行完成就会回到Activity,无法退出。

写了一个不太成功的“流氓”app~
但是如果使用虚拟键导航,在华为EMUI10上连按3次HOME键一定会退出来,在原声Android10上则会有延时,也就是说按home键退出到手机桌面之后一两秒app才会被重新启动,有时候还不会启动。

别忘了在清单文件中注册广播接收者,把优先级设置为最高。

那么如何阻止别的app启动呢然并不能阻止,但是我们可以把我们的APP重新叫起来。注意这里并不是进程保活,之前我也想做双进程或者1像素UI什么的,但是现在的高版本Android早就把洞堵上了,人腾讯的app可是把所有保活手段都用上了,还有白名单,咱可没这本事。
而且既然只要保证我们的Activity在前台,可以使用暴力一点的方法。比如在OnStop()的时候重新叫起Activity。

可以看到当canFinish为true的时候什么都不做,如果不为true,那么我们先清空Activity栈,然后重新startActivity。这里清栈的目的是为了防止OnStop的时候Activity发现栈中有实例不去重新创建。

然而很多时候这里不会执行到,Android会忽略在OnStop中做的这个请求,让别的app启动。

所以我们可以更加暴力点,直接开一个service去启动Activity。

package com.bai.psychedelic.voicequit;import android.app.ActivityManager;import android.app.Service;import android.app.usage.UsageStats;import android.app.usage.UsageStatsManager;import android.content.ComponentName;import android.content.Context;import android.content.Intent;import android.os.IBinder;import android.util.Log;import androidx.annotation.Nullable;import java.util.Collections;import java.util.Comparator;import java.util.List;import java.util.concurrent.ExecutorService;import java.util.concurrent.Executors;public class RebootService extends Service {    public static final String TAG = "RebootService";    private Context context;    @Nullable    @Override    public IBinder onBind(Intent intent) {return null;    }    @Override    public void onCreate() {super.onCreate();context = this;    }    @Override    public int onStartCommand(Intent intent, int flags, int startId) {ExecutorService executorService = Executors.newSingleThreadExecutor();executorService.execute(new Runnable() {    @Override    public void run() { while (true){try { Thread.sleep(50); if (!MainActivity.isAppVisible && !MainActivity.canFinish ) {     Intent intent = new Intent(context,MainActivity.class);     intent .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);     startActivity(intent);     Log.d(TAG,"onStartCommand startActivity"); }} catch (Exception e) { e.printStackTrace();} }    }});return super.onStartCommand(intent,

                                                        

声明:本站部分文章及图片源自用户投稿,如本站任何资料有侵权请您尽早请联系jinwei@zod.com.cn进行处理,非常感谢!

上一篇 2020年1月7日
下一篇 2020年1月7日

相关推荐