我有一个EditText
,我在其中设置错误或在文本更改后解除错误。然而不知何故,当我试图从EditText
方法访问afterTextChanged()
时,我正在获得NPE。
phone_number_input.addTextChangedListener(object : TextWatcher() {
...
override fun afterTextChanged(s: Editable?) {
if (isValid(s.toString())
phone_number_input.error = null // <-- NPE happens here
else
phone_number_input.error = "Number is invalid"
}
})
它不是经常复制,但在上个月,从Android 4.4.2到6.0.1的不同设备上发生了数十次崩溃。
怎么会发生这种情况?如果Fragment
被摧毁,不应该召唤TextWatcher
,对吗?如何预防?
怎么会发生这种情况?
最有可能的是,当发生这种情况时,您的应用会在用户输入时前往前台(例如,由于来电)。
如果
Fragment
被摧毁,不应该召唤TextWatcher
,对吗?
对。但是你错过了Fragment
和Layout
在“内部”膨胀的命令被摧毁。这两个人的破坏不是同时进行的 - Layout
首先被摧毁。
正如你所看到的,TextWatcher
是一个anonymous inner class instance that keeps reference to its outer class,你的Fragment
,它最后会被摧毁。这里的关键点是,来自EditText
的TextWatcher
中的任何文本更改都是异步完成的 - 您的应用程序的进程视图从系统中的另一个进程获得“通知”,软键盘应用程序(default one)。
如果这样的“通知”一次出现你的EditText
已被销毁但你的Fragment
没有,你得到NPE。
如何预防?
只需使用phone_number_input?.error = ...