遇到问题是这样的
05-02 14:58:57.154 15241 15241 E AndroidRuntime: FATAL EXCEPTION: main
05-02 14:58:57.154 15241 15241 E AndroidRuntime: Process: com.android.phone, PID: 15241
05-02 14:58:57.154 15241 15241 E AndroidRuntime: java.lang.SecurityException: Invalid component: ComponentInfo{com.android.settings/com.android.settings.Settings$IccLockSettingsActivity}
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.os.Parcel.readException(Parcel.java:1942)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.os.Parcel.readException(Parcel.java:1888)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.autofill.IAutoFillManager$Stub$Proxy.startSession(IAutoFillManager.java:413)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.autofill.AutofillManager.startSessionLocked(AutofillManager.java:836)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.autofill.AutofillManager.notifyViewEntered(AutofillManager.java:474)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.autofill.AutofillManager.notifyViewEntered(AutofillManager.java:453)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.View.notifyEnterOrExitForAutoFillIfNeeded(View.java:7022)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.View.onWindowFocusChanged(View.java:12141)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.widget.TextView.onWindowFocusChanged(TextView.java:9895)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.View.dispatchWindowFocusChanged(View.java:12106)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewGroup.dispatchWindowFocusChanged(ViewGroup.java:1416)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.view.ViewRootImpl$ViewRootHandler.handleMessage(ViewRootImpl.java:4283)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.os.Handler.dispatchMessage(Handler.java:108)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.os.Looper.loop(Looper.java:206)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at android.app.ActivityThread.main(ActivityThread.java:6735)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at java.lang.reflect.Method.invoke(Native Method)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:240)
05-02 14:58:57.154 15241 15241 E AndroidRuntime: at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:845)
05-02 14:58:57.159 1020 1564 W ActivityManager: Force finishing activity com.android.settings/.Settings$IccLockSettingsActivity
05-02 14:58:57.166 1020 1099 I ActivityManager: Showing crash dialog for package com.android.phone u0
问题原因
该 Issue 是某个 Google security patch 导致的。
在那个 Security patch 中,在进入和退出 EditText 时会进行 Auto fill 的 Security check。
可以采用 Disable auto fill 的方式来解决该问题,具体修改方法如下:
使用的 Settings 中的文件"EditPinPreference.java"。
解决方法:
文件路径为:/packages/apps/Settings/src/com/android/settings/EditPinPreference.java
在方法"onBindDialogView()"中增加 Disable auto fill 的 Code,如下所示:
protected void onBindDialogView(View view) {
super.onBindDialogView(view);
final EditText editText = (EditText) view.findViewById(android.R.id.edit);
if (editText != null) {
editText.setInputType(InputType.TYPE_CLASS_NUMBER |
InputType.TYPE_NUMBER_VARIATION_PASSWORD);
editText.setImportantForAutofill(
View.IMPORTANT_FOR_AUTOFILL_NO_EXCLUDE_DESCENDANTS);
}
}
查看资料
https://www.jianshu.com/p/531ce99bd961
这个功能也不是什么新的亮点,用过Chrome浏览器的人对自动填充功能肯定有所体验,这次Google把它搬到了手机上,目的自然是想打通各个平台。但是同时问题也来了,在某些页面我并不是很想使用自动填充功能,因为填充的数据实在是不怎么友好,比如对于一个简单的搜索框,系统给出的自动填充建议竟然是机主的姓名。再者就是有些敏感数据并不想保存到自动填充的表单里面,所以笔者根据参考官方文档和一些博文整理了本篇文章。
作为一个开发者,如何来控制自动填充功能呢?在Android O Developer Preview 3中google提供了一些解决办法,即从sdk26开始,所有的视图中新增了一个android:importantForAutofill
的属性,以及相应的一个方法setImportantForAutofill()
来控制自动填充功能,具体的细节不细说,可参考官方文档,这里只简单说一下如何在代码里控制自动填充功能。
通过在 layout 文件中给控件设置
android:importantForAutofill="no"
或在代码中调用View
的setImportantForAutofill(View.IMPORTANT_FOR_AUTOFILL_NO)
方法。通过在 activity 的
onCreate()
方法中加入如下代码:getWindow()
.getDecorView()
.setImportantForAutofill(View.IMPORTANT_FOR_AUTOFILL_NO_EXCLUDE_DESCENDANTS);
```
在这种情况下,这些控件的数据也不会提供给自动填充服务,不会被记录。对于一个视图容器来说,如果设置了noExcludeDescendants
或者IMPORTANT_FOR_AUTOFILL_NO_EXCLUDE_DESCENDANTS
,也就意味着不仅是该容器自身还是它的所有子视图,都会受到相关影响。
对于某些安全性要求较高或者某些特殊的页面,自动填充不再是一个优势,反而带来影响的时候,我们可以用上面的两个方式来禁止自动填充功能。
对于某些系统版本,比如 Android O Preview 2中,以上两个方式不会生效。这时候就可以用AutofillManager
先检查一下自动填充是否开启,如果开启了,采取回避行动。
if (getSystemService(android.view.autofill.AutofillManager.class).isEnabled()) {
Toast.makeText(this, "Ick!", Toast.LENGTH_LONG).show();
finish();
}