Play商店预发布报告中的Android应用崩溃,但可在真实设备中使用 [英] Android app crash in play store prelaunch report but working in real device

查看:107
本文介绍了Play商店预发布报告中的Android应用崩溃,但可在真实设备中使用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

无法跟踪项目中的崩溃,我在Play商店预启动部分中收到此错误,单击EditText时显示该错误,并且出现了错误.但在真实设备上没有崩溃.

Not able to track crash in the project, I got this error in play store pre-launch section, it showing on click of EditText, it got the error. but not getting any crash on a real device.

问题:java.lang.IndexOutOfBoundsException:setSpan(4 ... 4)结束于长度0

Fatal Exception: java.lang.IndexOutOfBoundsException: setSpan (4 ... 4) ends beyond length 0
       at android.text.SpannableStringBuilder.checkRange(SpannableStringBuilder.java:1096)
       at android.text.SpannableStringBuilder.setSpan(SpannableStringBuilder.java:671)
       at android.text.SpannableStringBuilder.setSpan(SpannableStringBuilder.java:664)
       at android.text.Selection.setSelection(Selection.java:76)
       at android.text.Selection.setSelection(Selection.java:87)
       at android.widget.EditText.setSelection(EditText.java:98)
       at android.widget.EditText.performAccessibilityActionInternal(EditText.java:138)
       at android.view.View.performAccessibilityAction(View.java:8892)
       at android.view.AccessibilityInteractionController.performAccessibilityActionUiThread(AccessibilityInteractionController.java:668)
       at android.view.AccessibilityInteractionController.-wrap6(AccessibilityInteractionController.java)
       at android.view.AccessibilityInteractionController$PrivateHandler.handleMessage(AccessibilityInteractionController.java:1194)
       at android.os.Handler.dispatchMessage(Handler.java:102)
       at android.os.Looper.loop(Looper.java:148)
       at android.app.ActivityThread.main(ActivityThread.java:5459)
       at java.lang.reflect.Method.invoke(Method.java)
       at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:728)
       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)

推荐答案

在发布前的报告和FireBase测试实验室中,我都看到了同样的错误.我花了几个小时研究此问题,并且确定这是一个仅会影响SDK< = 23的错误,并由AccessibilityNodeInfo#performAction(ACTION_SET_TEXT)触发. 看来此方法完全忽略了maxLength属性,该属性继而导致IndexOutOfBoundsException.

I was seeing his same error, both in the pre-launch report and in FireBase test lab. I spent several hours looking into this and I am sure it is a bug that only affects SDK <= 23 and is triggered by AccessibilityNodeInfo#performAction(ACTION_SET_TEXT). It seems this method completely ignores the maxLength attribute which in turn causes the IndexOutOfBoundsException.

您可以使用以下代码复制相同的异常,并确保字符串"1234"长于您的maxLength:

You can duplicate this same exception with the following code, making sure the string "1234" is longer than your maxLength:

 Bundle arguments = new Bundle();
 arguments.putCharSequence(AccessibilityNodeInfo.ACTION_ARGUMENT_SET_TEXT_CHARSEQUENCE, "1234");
 mEditText.performAccessibilityAction(AccessibilityNodeInfo.ACTION_SET_TEXT, arguments);

那么,该怎么办?

一个选择是忽略它,因为它可能会影响很小一部分用户.除非您认为您可能有许多用户使用辅助功能来输入文本,并且他们还使用了较早的SDK(< = 23).

One option is to just ignore it as it is likely to affect a very small subset of users. that is unless you think you might have many users using accessibility functions to enter text and they are also using older SDKs (<= 23).

另一种选择是将build.gradle中的minSDKVersion设置为24.如果您使用SDK< = 23的用户很多,这可能会造成伤害.

Another option would be to set your minSDKVersion in your build.gradle to 24. This might hurt if you have a lot of users using SDK <= 23

第三个选择是使用我想出的这个非常丑陋的解决方法:

A third option would be to use this very ugly workaround I came up with:

if(Build.VERSION.SDK_INT <= 23){
        ViewGroup rootView = findViewById(R.id.your_layout_that_contains_edittexts);
        ArrayList<View> views = rootView.getTouchables();
        for(View view : views){
            if(view instanceof EditText){
                EditText mEditText = (EditText)view;
                mEditText.setAccessibilityDelegate(new View.AccessibilityDelegate() {
                    @Override
                    public boolean performAccessibilityAction(View host, int action, Bundle arguments) {

                        if (action == AccessibilityNodeInfo.ACTION_SET_TEXT) {
                            //do something here to make sure index out of bounds does not occur
                            int maxLength = 0;
                            for(InputFilter filter : mEditText.getFilters()){
                                if(filter instanceof InputFilter.LengthFilter)  {
                                    maxLength = ((InputFilter.LengthFilter)filter).getMax();
                                }
                            }

                            Set<String> keys  = arguments.keySet();
                            for(String key : keys){
                                if(arguments.get(key) instanceof  CharSequence){
                                    if(arguments.get(key) != null) {
                                        arguments.putCharSequence(key, ((CharSequence) arguments.get(key)).subSequence(0, maxLength));
                                        mEditText.setText(arguments.getCharSequence(key));
                                    }
                                }
                            }
                        }
                        return true;
                    }
                });

            }
        }

    }

好,所以我确实说这很丑,但是确实有效.用包含所有EditText的布局的ID替换your_layout_that_contains_edittexts.

OK, so I did say it was ugly, but it does work. Replace your_layout_that_contains_edittexts with the id of a layout that contains all your EditTexts.

基本上,如果SDK <= 23,它将循环遍历ViewGroup中的所有EditText,并通过AccessibilityDelegate覆盖performAccessibilityAction,并确保输入的文本不会超过EditText的maxLength值.

Basically, if SDK <= 23, it cycles through all the EditTexts in the ViewGroup and for each one, overrides the performAccessibilityAction via AccessibilityDelegate and ensures that the text being entered never exceeds the EditText's maxLength value.

这篇关于Play商店预发布报告中的Android应用崩溃,但可在真实设备中使用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆