Android ViewPager выдает исключение IndexOutOfBounds при установке текущего элемента / страницы

У меня есть ViewPager с тремя элементами. Я пытаюсь настроить ViewPager для просмотра самой правой страницы (которая будет вторым элементом). Это возвращает исключение IndexOutOfBounds, хотя я знаю, что индекс должен быть в границах. Вот точный стек:

02-22 12:22:50.256: E/AndroidRuntime(384): FATAL EXCEPTION: main
02-22 12:22:50.256: E/AndroidRuntime(384): java.lang.IndexOutOfBoundsException: index=1 count=0
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.addInArray(ViewGroup.java:2050)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.addViewInner(ViewGroup.java:1994)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.addViewInLayout(ViewGroup.java:1958)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.addViewInLayout(ViewGroup.java:1939)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.support.v4.view.ViewPager.addView(ViewPager.java:917)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.addView(ViewGroup.java:1828)
02-22 12:22:50.256: E/AndroidRuntime(384):  at us.tagverse.pagertest.MasterActivity$PAdapter.instantiateItem(MasterActivity.java:518)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.support.v4.view.PagerAdapter.instantiateItem(PagerAdapter.java:110)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.support.v4.view.ViewPager.addNewItem(ViewPager.java:649)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.support.v4.view.ViewPager.populate(ViewPager.java:783)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.support.v4.view.ViewPager.onMeasure(ViewPager.java:1016)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.View.measure(View.java:8313)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:3138)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.widget.LinearLayout.measureChildBeforeLayout(LinearLayout.java:1017)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.widget.LinearLayout.measureVertical(LinearLayout.java:386)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.widget.LinearLayout.onMeasure(LinearLayout.java:309)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.View.measure(View.java:8313)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:3138)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.widget.FrameLayout.onMeasure(FrameLayout.java:250)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.View.measure(View.java:8313)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:3138)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.widget.FrameLayout.onMeasure(FrameLayout.java:250)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.View.measure(View.java:8313)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewRoot.performTraversals(ViewRoot.java:839)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.view.ViewRoot.handleMessage(ViewRoot.java:1859)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.os.Handler.dispatchMessage(Handler.java:99)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.os.Looper.loop(Looper.java:123)
02-22 12:22:50.256: E/AndroidRuntime(384):  at android.app.ActivityThread.main(ActivityThread.java:3683)
02-22 12:22:50.256: E/AndroidRuntime(384):  at java.lang.reflect.Method.invokeNative(Native Method)
02-22 12:22:50.256: E/AndroidRuntime(384):  at java.lang.reflect.Method.invoke(Method.java:507)
02-22 12:22:50.256: E/AndroidRuntime(384):  at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:839)
02-22 12:22:50.256: E/AndroidRuntime(384):  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:597)
02-22 12:22:50.256: E/AndroidRuntime(384):  at dalvik.system.NativeStart.main(Native Method)

Обратите внимание, что причиной является java.lang.IndexOutOfBoundsException: index = 1 count = 0 . Это будет означать, что количество страниц / элементов равно 0, а индекс, который я запрашиваю, равен 1. Ни то, ни другое не соответствует действительности. Вот как я вызываю свой ViewPager и запрашиваю данную страницу:

ViewPager pager = (ViewPager) findViewById(R.id.ma_viewcontainer);
PAdapter adapter = new PAdapter();
pager.setAdapter(adapter);
pager.setCurrentItem(2);

Обратите внимание, что этот вызов не дает никаких ошибок и правильно устанавливает текущий элемент в средний элемент (индекс 1):

ViewPager pager = (ViewPager) findViewById(R.id.ma_viewcontainer);
PAdapter adapter = new PAdapter();
pager.setAdapter(adapter);
pager.setCurrentItem(1);

У меня есть счетчик 3 элемента в пейджере просмотра. Вот мой полный класс PAdapter, который расширяет класс PagerAdapter:

private class PAdapter extends PagerAdapter implements TitleProvider {

    private int COUNT = 3;

    private static final int SETTINGS_ACTIVITY = 0;
    private static final int MAIN_ACTIVITY = 1;
    private static final int FRIEND_LIST_ACTIVITY = 2;

    @Override
    public int getCount() {
        return COUNT;
    }

    @Override
    public Object instantiateItem(View collection, int position) {
        LinearLayout layout = new LinearLayout(getApplicationContext());
        LayoutInflater inflater = (LayoutInflater) getApplicationContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
        switch(position) {
        case MAIN_ACTIVITY :
            layout = (LinearLayout) inflater.inflate(R.layout.main, null, false);
            initMainLayout(layout);
            break;
        case SETTINGS_ACTIVITY :
            layout = (LinearLayout) inflater.inflate(R.layout.settings, null, false);
            initSettingsLayout(layout);
            break;
        case FRIEND_LIST_ACTIVITY :
            layout = (LinearLayout) inflater.inflate(R.layout.friend_list, null, false);
            initFriendListLayout(layout);
            break;
        }
        ((ViewPager)collection).addView(layout, position);
        return layout;
    }

    @Override
    public void destroyItem(View collection, int position, Object view) {
        ((ViewPager)collection).removeView((LinearLayout)view);
    }

    @Override
    public boolean isViewFromObject(View v, Object o) {
        return v == (LinearLayout)o;
    }

    @Override
    public void finishUpdate(View arg0) {
        //no need
    }

    @Override
    public void restoreState(Parcelable arg0, ClassLoader arg1) {
        //no need
    }

    @Override
    public Parcelable saveState() {
        return null;
    }

    @Override
    public void startUpdate(View arg0) {
        //no need
    }

    @Override
    public String getTitle(int position) {
        Resources res = getApplicationContext().getResources();
        switch(position) {
        case MAIN_ACTIVITY :
            return res.getString(R.string.app_name);
        case SETTINGS_ACTIVITY :
            return res.getString(R.string.settings);
        case FRIEND_LIST_ACTIVITY :
            return res.getString(R.string.friend_list);
        default :
            return null;
        }
    }
}

Строка ((ViewPager) collection) .addView (layout, position); вызывает сбой.

Как видите, три пункта. Использование setCurrentItem () с параметром 0 или 1 работает нормально, но 2 вызывает эту странную ошибку. У меня закончились идеи, чтобы решить эту проблему ... к сожалению, ViewPager, похоже, находится в некоторых неизведанных водах Android. Если у кого-то есть представление о том, как решить эту проблему, мы будем очень признательны.Спасибо!

РЕДАКТИРОВАТЬ: Согласно предложению Шерифа, я попытался записать счетчик потомков через collection.getChildCount () и получил следующий результат:

02-22 15:20:42.274: E/children count(645): count: 0
02-22 15:20:42.454: E/children count(645): count: 1
02-22 15:20:42.594: E/children count(645): count: 2

Это интересно. Это говорит мне о том, что он создает пустой PagerAdapter и добавляет их по одному. instantiateItem () вызывается 3 раза для трех видимых представлений (в центре, слева и справа). Поэтому я добавил этот блок кода в метод instantiateItem () :

if(((ViewPager)collection).getChildCount() ==  2) {
    ((ViewPager)collection).setCurrentItem(2);
}

Итак, только если счетчик установлен равным 2, он установит страницу в 2 (это хакерское решение, которое не полностью решить проблему, но попробовать стоило). У меня был похожий стек ошибок, который сначала указывал на строку: ((ViewPager) collection) .setCurrentItem (2); , затем ((ViewPager) collection) .addView (layout, position); .

Надеюсь, это поможет вам понять.

17
задан JMRboosties 22 February 2012 в 23:33
поделиться