Я использую библиотеку поддержки, и у меня есть фрагмент (я буду называть «MyFragment»), реализующий метод, вызванный одним из просмотра фрагмента во время события OnClick. OnClickListener устанавливается в OnActivityCreate метод так:GetView(), возвращающий null в обратном вызове OnClickListener
@Override
public void onActivityCreated(Bundle inState) {
super.onActivityCreated(inState);
ViewGroup base = (ViewGroup) getView();
TextView tv = (TextView) base.findViewById(R.id.monografiat);
tv.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
showStuff(); // MyFragment:150
}
});
}
где showStuff() вызывает изменения в поле зрения фрагмента, что-то же просто, как обновление видимость элемента:
private void showStuff() { //MyFragment:95
ViewGroup base = (ViewGroup) getView();
LinearLayout ll = (LinearLayout) base.findViewById(R.id.someview); // MyFragment:97
ll.setVisibility(View.VISIBLE);
}
Everything отлично работает на моих тестах, и то же самое можно сказать о большинстве моих пользователей, однако сегодня я получил один отчет ANR от консоли разработчика Google Play, в котором говорится, что приложение потерпело крах для пользователя с исключением NullPointerException на линии:
LinearLayout ll = (LinearLayout) base.findViewById(R.id.someview);
означает, что:
ViewGroup base = (ViewGroup) getView();
возвращается нуль. Это отчет:
java.lang.NullPointerException
at mypackage.MyFragment.showStuff(MyFragment.java:97)
at mypackage.MyFragment.access$0(MyFragment.java:95)
at mypackage.MyFragment$2.onClick(MyFragment.java:150)
at android.view.View.performClick(View.java:2538)
at android.view.View$PerformClick.run(View.java:9152)
at android.os.Handler.handleCallback(Handler.java:587)
at android.os.Handler.dispatchMessage(Handler.java:92)
at android.os.Looper.loop(Looper.java:123)
at android.app.ActivityThread.main(ActivityThread.java:3687)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:507)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:842)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:600)
at dalvik.system.NativeStart.main(Native Method)
Я исправил проблему (или я так думаю, потому что я не способ размножения ...), просто окружающие обижая линии с:
if(base != null) {
}
моя лучшая догадка заключается в том, что обратный вызов был запланирован после того, как onDestroyView был вызван в MyFragment, в результате чего getView() возвращает null.
Тем не менее, я весьма озадачен этой ошибкой, поэтому я хотел бы ваши идеи по этому вопросу:
при условии, что мой hypotesys правильно, это нормально для обратного вызова OnClick будет выполняться когда макет отсутствует, или я могу рассматривать это поведение как ошибку (честно: вид был явно там, когда я щелкнул его, почему он должен умереть на мне)?
Эта проблема связана с тем, что я пользуюсь библиотекой поддержки (последняя версия, 13 мая 2013 г.)?
Если это не ошибка, и мне что-то не хватает, не могли бы вы указать мне соответствующую документацию?
Благодарим за внимание!
Любые причины, по которым вы используете 'ViewGroup' вместо просто' View'? Можете ли вы также проверить, определено ли 'R.id.someview' в представлении' getView() '? – Vikram
Не в этот конкретный момент, однако я знаю, что макет является подклассом ViewGroup (а Java в противном случае бросает ClassCastException). Что касается R.id.someview, если соответствующее представление не будет найдено, исключение было бы выбрано в строке 98 (вместо этого на 97) – Rick77
Вы правы, я полностью это пропустил. – Vikram