Android 去除锁屏功能和"Android is strating"画面
一般来说对于很多Android 产品,客户希望自己的app作为launch,并且开机直接进去app显示画面,上述feature 可以分为以下几个部分:1. 使用客户app 替换原声launch app;2. 跳过进入系统前的密码验证阶段,直接进入系统(锁屏);
一.除去Android 锁屏功能
这个部分根据平台不同改法可能会不同,我用的是Android Q平台,选取了最为简单的改法:
修改frameworks/base/packages/SettingsProvider/res/values/defaults.xml 文件
<string name="def_charging_started_sound" translatable="false">/product/media/audio/ui/ChargingStarted.ogg</string>
<!-- sound trigger detection service default values -->
<integer name="def_max_sound_trigger_detection_service_ops_per_day" translatable="false">1000</integer>
<integer name="def_sound_trigger_detection_service_op_timeout" translatable="false">15000</integer>
- <bool name="def_lockscreen_disabled">false</bool>
+ <bool name="def_lockscreen_disabled">true</bool>
<bool name="def_device_provisioned">false</bool>
将def_lockscreen_disabled 改为true;
二."Android is strating"画面
如果把锁屏方式设置为无,重启之后可能是可以先看到一个“Android is strating”的页面,然后才真正出现了Launcher。通过查询代码可以得知"Android is strating"画面是etting中的一个Activity:“FallbackHome” ,改Activity声明了CATEGORY_HOME,但是Launcher也声明了CATEGORY_HOME,为啥先进入FallbackHome而不是Launcher呢?一开始我认为是CATEGORY_HOME优先级的原因导致。
在setting中定义的Activity:
2294 <activity android:name=".CryptKeeper"
2295 androidprv:systemUserOnly="true"
2296 android:immersive="true"
2297 android:launchMode="singleTop"
2298 android:excludeFromRecents="true"
2299 android:theme="@style/Theme.CryptKeeper"
2300 android:configChanges="mnc|mcc|keyboard|keyboardHidden|uiMode"
2301 android:windowSoftInputMode="adjustResize"
2302 android:screenOrientation="nosensor"
2303 android:process=":CryptKeeper">
2304 <intent-filter android:priority="10">
2305 <action android:name="android.intent.action.MAIN" />
2306 <category android:name="android.intent.category.HOME" />
2307 <category android:name="android.intent.category.DEFAULT" />
2308 </intent-filter>
2309 </activity>
2310
2311 <!-- Triggered when user-selected home app isn't encryption aware -->
2312 <activity android:name=".FallbackHome"
2313 android:excludeFromRecents="true"
2314 android:label=""
2315 android:screenOrientation="nosensor"
2316 android:taskAffinity="com.android.settings.FallbackHome"
2317 android:theme="@style/FallbackHome">
2318 <intent-filter android:priority="-1000">
2319 <action android:name="android.intent.action.MAIN" />
2320 <category android:name="android.intent.category.HOME" />
2321 <category android:name="android.intent.category.DEFAULT" />
2322 </intent-filter>
2323 </activity>
可以看到FallbackHome相关的优先级为10,于是我把Launcher的优先级调整到20,但是并没有任何效果,FallbackHome任然会出现,非常头疼,然后就是长时间的百度、论坛过程。。。。最后我决定先梳理FallbackHome的代码逻辑看看,能不能通过修改FallbackHome画面来达到屏蔽显示过程;
下面来简单分析下FallbackHome画面加载过程和退出条件:
首先系统启动后会自动加载CATEGORY_HOME
@Override
108 protected void onResume() {
109 super.onResume();
110 if (mProvisioned) {
111 mHandler.postDelayed(mProgressTimeoutRunnable, PROGRESS_TIMEOUT);
112 }
113 }
private final Runnable mProgressTimeoutRunnable = () -> {
52 View v = getLayoutInflater().inflate(
53 R.layout.fallback_home_finishing_boot, null /* root */);
54 setContentView(v);
55 v.setAlpha(0f);
56 v.animate()
57 .alpha(1f)
58 .setDuration(500)
59 .setInterpolator(AnimationUtils.loadInterpolator(
60 this, android.R.interpolator.fast_out_slow_in))
61 .start();
62 getWindow().addFlags(LayoutParams.FLAG_KEEP_SCREEN_ON);
63 };
显示文言:packages/apps/Settings/res/layout/fallback_home_finishing_boot.xml
1<?xml version="1.0" encoding="utf-8"?>
.......
17
18<FrameLayout
19 xmlns:android="http://schemas.android.com/apk/res/android"
20 android:layout_width="match_parent"
21 android:layout_height="match_parent"
22 android:background="#80000000"
23 android:forceHasOverlappingRendering="false">
24
25 <LinearLayout
26 android:layout_width="wrap_content"
27 android:layout_height="wrap_content"
28 android:orientation="vertical"
29 android:layout_gravity="center"
30 android:layout_marginStart="16dp"
31 android:layout_marginEnd="16dp">
32
33 <TextView
34 android:layout_width="wrap_content"
35 android:layout_height="wrap_content"
36 android:textSize="20sp"
37 android:textColor="?android:attr/textColorPrimary"
38 android:text="@*android:string/android_start_title"/>
39
40 <ProgressBar
41 style="@android:style/Widget.Material.ProgressBar.Horizontal"
42 android:layout_width="match_parent"
43 android:layout_height="wrap_content"
44 android:layout_marginTop="12.75dp"
45 android:colorControlActivated="?android:attr/textColorPrimary"
46 android:indeterminate="true"/>
47
48 </LinearLayout>
49</FrameLayout>
设置屏幕亮:getWindow().addFlags(LayoutParams.FLAG_KEEP_SCREEN_ON);
于是我尝试修改显示文言 :
并且将getWindow().addFlags(LayoutParams.FLAG_KEEP_SCREEN_ON); 改为
getWindow().addFlags(LayoutParams.FLAG_KEEP_SCREEN_OFF);
private final Runnable mProgressTimeoutRunnable = () -> {
52 //View v = getLayoutInflater().inflate(
53 // R.layout.fallback_home_finishing_boot, null /* root */);
54 //setContentView(v);
55 //v.setAlpha(0f);
56 //v.animate()
57 // .alpha(1f)
58 // .setDuration(500)
59 // .setInterpolator(AnimationUtils.loadInterpolator(
60 // this, android.R.interpolator.fast_out_slow_in))
61 // .start();
62 getWindow().addFlags(LayoutParams.FLAG_KEEP_SCREEN_OFF);
63 };
通过验证发现, 开机过程"Android is starting"画面已经消失了,但是取而代之的是一段黑屏,相当于变相增加了开机时间,所以这并不是最终的解决方案,于是又是一番百度、论坛。。终于找到了关键点:DirectBoot模式
具体什么是DirectBoot模式,下面一篇文章很详细,干兴趣可以了解一下。
https://blog.csdn.net/ws6013480777777/article/details/86662739
然后通过对比FallbackHome和launcher app,Settings是在Manifest中声明了android:directBootAware=“true”,而Launcher没有,所以在此情况下,因此刚开机时,其实只有FallbackHome这个页面会被检索到,也就不会直接进入launcher。然后FallbackHome这个界面会一直检测当前是否已经具备唤醒正常Launcher的条件,如果OK,就finish掉自己。
所以,如果想自己的launcher app能在directboot阶段启动的话,只需要修改launcher app相关代码实现就ok了,具体还有许多坑,具体过程不加以叙述,直接提供一个我验证过的方法:
修改launcher app的 AndroidManifest.xml文件:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:androidprv="http://schemas.android.com/apk/prv/res/android"
coreApp="true"
package="com.xxx.xxxoapp">
<uses-permission android:name="android.permission.CAMERA"/>
......省略
<uses-permission android:name="android.permission.SHUTDOWN"/>
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:directBootAware="true"
android:testOnly="false"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity"
androidprv:systemUserOnly="true">
<intent-filter android:priority="20">
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER"/>
<category android:name="android.intent.category.DEFAULT"/>
</intent-filter>
</activity>
</application>
</manifest>
其中比较关键的有:
xmlns:androidprv="http://schemas.android.com/apk/prv/res/android"
android:directBootAware="true"
androidprv:systemUserOnly="true">
<intent-filter android:priority="20">
大家可以先修改原声系统中launcher3 来验证是否能实现,然后再移植自己的launcher app。
本文为原创文章,转载请注明出处!!!!