ViewPager加載Fragment出現空白不顯示問題


場景一:在Fragment中使用TabLayout+ViewPager,ViewPager加載不同Fragment,tablayout的Tab顯示而Fragment不顯示

使用tablayout需導入design庫implementation 'com.android.support:design:26.1.0'
  • xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <android.support.design.widget.TabLayout
        android:id="@+id/tablayout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"/>

    <android.support.v4.view.ViewPager
        android:id="@+id/viewpager"
        android:layout_width="match_parent"
        android:layout_height="match_parent"/>


</LinearLayout>
  • activity
public class MainActivity extends AppCompatActivity {
    private ViewPager viewPager;
    private TabLayout mTablayout;
    private List<Fragment> fragmentList;
    private String[] title = {"第一", "第二", "第三"};
    private MyPagerAdapter2 mAdapter;

    private <T extends View> T bindView(int id) {
        return (T) findViewById(id);
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        viewPager = bindView(R.id.viewpager);
        mTablayout = bindView(R.id.tablayout);
        initData();

    }

    private void initData() {
        fragmentList = new ArrayList<>();
        fragmentList.add(new OneFragment());
        fragmentList.add(new TwoFragment());
        fragmentList.add(new ThreeFragment());
        mAdapter = new MyPagerAdapter2(getSupportFragmentManager());
        mTablayout.setTabMode(TabLayout.MODE_FIXED);//均分屏幕
        mTablayout.setTabTextColors(Color.BLACK, Color.RED);//第一個參數為未選中字體顏色,第二個為選中tab字體顏色
        mTablayout.setSelectedTabIndicatorColor(Color.RED);//選中tab下劃線顏色
        mTablayout.setSelectedTabIndicatorHeight(5);//選中tab下劃線高度
        viewPager.setAdapter(mAdapter);
        mTablayout.setupWithViewPager(viewPager);
        mTablayout.addOnTabSelectedListener(new TabLayout.OnTabSelectedListener() {
            @Override
            public void onTabSelected(TabLayout.Tab tab) {
                viewPager.setCurrentItem(tab.getPosition());
            }

            @Override
            public void onTabUnselected(TabLayout.Tab tab) {

            }

            @Override
            public void onTabReselected(TabLayout.Tab tab) {

            }
        });

    }


    private class MyPagerAdapter2 extends FragmentPagerAdapter {

        public MyPagerAdapter2(FragmentManager fm) {
            super(fm);
        }

        @Override
        public Fragment getItem(int position) {
            return fragmentList != null ? fragmentList.get(position) : null;
        }

        @Override
        public int getCount() {
            return fragmentList != null ? fragmentList.size() : 0;
        }

        @Override
        public boolean isViewFromObject(View view, Object object) {
                      return view == object;
//            return super.isViewFromObject(view, object);
        }

        @Override
        public CharSequence getPageTitle(int position) {
            return title[position];
        }
    }
}

代碼看上去很正常沒毛病,實際結果:tablayout顯示而fragment全部不顯示
??->界面不顯示這還了得,趕緊找原因

  • 分析:
    tablayout顯示,而且title是關聯viewpager時添加顯示的,說明adapter中數據源應該是沒問題的,應該是控制fragment顯示的方法出現問題。最終定位到方法isViewFromObject,重寫此方法導致fragment不顯示了

  • 查看源碼發現,它是PagerAdapter里面的一個抽象方法

  /**
     * Determines whether a page View is associated with a specific key object
     * as returned by {@link #instantiateItem(ViewGroup, int)}. This method is
     * required for a PagerAdapter to function properly.
     *
     * @param view Page View to check for association with <code>object</code>
     * @param object Object to check for association with <code>view</code>
     * @return true if <code>view</code> is associated with the key object <code>object</code>
     */
    public abstract boolean isViewFromObject(View view, Object object);

而FragmentPagerAdapter繼承自PageAdapter,同時已經實現了該方法

FragmentPagerAdapter截圖

   @Override
    public boolean isViewFromObject(View view, Object object) {
        return ((Fragment)object).getView() == view;
    }

在寫適配器時,錯誤重寫了方法isViewFromObject導致fragment不顯示

  • 解決辦法
1、在適配器中刪除該方法(推薦,系統已經實現該方法無需沖洗)
2、重寫后直接使用父類方法`
   @Override
    public boolean isViewFromObject(View view, Object object) { return super.isViewFromObject(view, object);}`
3、重寫
` @Override
    public boolean isViewFromObject(View view, Object object) { return view ==((Fragment) object).getView();}`
//2、3方法不建議,這樣做無任何意義
  • 說明
    在寫適配器時,一般來講直接extends FragmentPagerAdapter,必須重載方法只有以下三個
    /**
     * Return the Fragment associated with a specified position.
     */
    public abstract Fragment getItem(int position);
    /**
     * Return the number of views available.
     */
    public abstract int getCount();
   /**
    *constuctor
    */
   public FragmentPagerAdapter(FragmentManager fm) {
        mFragmentManager = fm;
    }

場景二:在Fragment中使用Tablayout+viewpager加載fragment,fragment出現空白情況

  • 1、同場景一
  • 2、在創建適配器對象時傳錯參數,在activity中使用時創建對象需傳入getSupportFragmentManager()作為參數,在fragment中使用時需要傳入getChildFragmentManager()作為參數
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容