【问题标题】:Replace fragment in a ViewPager替换 ViewPager 中的片段
【发布时间】:2017-06-01 16:09:39
【问题描述】:

我正在尝试用另一个片段替换 ViewPager 中的片段之一。

pager 由两个页面组成: Fragment1 , Fragment2 在fragment2里面,有一个按钮。当我单击该按钮时,它将用 Fragment3 替换当前片段 Fragment2。对于 Fragment2,我希望它被销毁,不再存在。

实现代码:

  • activity_main 的布局:

    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_width="match_parent"
        android:layout_height="?attr/actionBarSize"
        android:background="?attr/colorPrimary"
        app:layout_scrollFlags="scroll|enterAlways"
        app:popupTheme="@style/AppTheme.PopupOverlay">
    
    </android.support.v7.widget.Toolbar>
    
    <android.support.design.widget.TabLayout
        android:id="@+id/tabs"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"/>
    

  • 主要活动:

    private SectionsPageAdapter mSectionsPageAdapter;
    private ViewPager mViewPager;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        mSectionsPageAdapter = new SectionsPageAdapter(getSupportFragmentManager());
    
    
        mViewPager = (ViewPager) findViewById(R.id.container);
    
        setupViewPager(mViewPager);
    
        TabLayout tabLayout = (TabLayout) findViewById(R.id.tabs);
        tabLayout.setupWithViewPager(mViewPager);
    
         mSectionsPageAdapter.clearAll();              
    
    
    }
    
    private void setupViewPager(ViewPager viewPager) {
        SectionsPageAdapter adapter = new SectionsPageAdapter(getSupportFragmentManager());
        adapter.addFragment(new Tab1Fragment(), "Tab 1");
        adapter.addFragment(new Tab2Fragment(), "Tab 2");
        adapter.notifyDataSetChanged()
        viewPager.setAdapter(adapter);
    }
    
  • 适配器:

    public class SectionsPageAdapter extends FragmentPagerAdapter {
    
        private final List<Fragment> mFragmentList = new ArrayList<>();
        private final List<String> mFragmentTitleList = new ArrayList<>();
    
        public void addFragment(Fragment fragment, String title) {
            mFragmentList.add(fragment);
            mFragmentTitleList.add(title);
        }
    
        public SectionsPageAdapter(FragmentManager fm) {
            super(fm);
        }
    
        @Override
        public CharSequence getPageTitle(int position) {
            return mFragmentTitleList.get(position);
        }
    
        @Override
        public Fragment getItem(int position) {
            return mFragmentList.get(position);
        }
    
        @Override
        public int getCount() {
            return mFragmentList.size();
        }
    
    
    }
    
  • 片段2:

    public class Tab2Fragment extends Fragment {
        private static final String TAG = "Tab2Fragment";
    
        private Button btnTEST;
    
        @Nullable
        @Override
        public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
            View view = inflater.inflate(R.layout.tab2_fragment,container,false);
            btnTEST = (Button) view.findViewById(R.id.btnTEST2);
    
            btnTEST.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Toast.makeText(getActivity(), "TESTING BUTTON CLICK 2", Toast.LENGTH_SHORT).show();
                }
            });
    
            return view;
        }
    
    }
    

更新:

我尝试在适配器中实现 clearAll 方法,我注意到 mFragmentList.size() 返回 0 为什么?

public void addFragment(Fragment fragment, String title) {
    mFragmentList.add(fragment);
    mFragmentTitleList.add(title);
 Log.d("tmz",mFragmentList.size()+" From  addFragment");  // return 1 & 2
}


@Override
public int getCount() {
    return mFragmentList.size();
    Log.d("tmz",mFragmentList.size()+"getCount "); // return 2 

}



public void clearAll(){
    Log.d("tmz",mFragmentList.size()+" From  addFragment"); // return 0 why ?
    for(int i=0; i<mFragmentList.size(); i++)
    fragMan.beginTransaction().remove(mFragmentList.get(i)).commit();
    mFragmentList.clear();
    mFragmentList=new ArrayList<Fragment>();
    notifyDataSetChanged();
}

【问题讨论】:

  • 你在哪里调用 clearAll()?
  • 此外,您的 addFragment() 方法需要在其末尾调用 notifyDataSetChanged() 才能使添加生效。
  • 我对我的代码进行了更改,我将 clearAll() 放在 oncreate() 中只是为了测试 mFragmentList 的大小,但在我将 notifyDataSetChanged() 放在之后仍然给了我一个零设置适配器。
  • 如果你在调用setupViewPager()之后调用它,那么它不应该返回0。否则你可以在addFragment()中的某个地方放置一个断点并在运行时检查mFragmentList中的值.
  • 我做到了,添加 Fragment() 和 getCount() 的大小将是 2 ,但是对于 clearAll() 是零,我不知道为什么?

标签: android android-fragments android-viewpager android-tablayout


【解决方案1】:

从 mFragmentList(和 mFragmentTitleList)中删除并添加新的,然后调用 notifyDataSetChanged?还可以添加到您的SectionsPageAdapter,以便在收到通知时强制重绘ViewPager

public int getItemPosition(Object object) {
    return POSITION_NONE;
}

不是最有效的,但足以满足您的目的。对于适配器:

public void removeLastFragment() {
    if(mFragmentList.size()==0)
         return;
    mFragmentList.remove(mFragmentList.size()-1);
    mFragmentTitleList.remove(mFragmentTitleList.size()-1);
}

【讨论】:

  • 感谢您的快速响应,但我仍然不清楚,我可以将 removeLastFragment 放在 onClick 侦听器中,并将 getItemPosition 放在适配器中。如果我有 4 个标签,我想用新的替换第三个片段怎么办
  • 当我将 removeLastFragment 放入 Adapter 时也会出现错误:“列表中的添加 (android.support.v4.app.Fragment) 无法应用于 (int)
  • 我的错误,应该有remove 而不是添加,显然...如果您将有更多选项卡然后按索引删除并通过方法add(int index, E element) 在位置添加片段。用你的大脑,创造你的逻辑,我已经为你提供了所有需要的方法
  • 你检查更新的部分了吗,当我尝试访问 mFragmentList 大小时它给了我一个零为什么
【解决方案2】:

零是因为

SectionsPageAdapter adapter = new SectionsPageAdapter(getSupportFragmentManager());

重复了两次,我通过在选项卡内使用替换片段解决了我的问题

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-01-31
    • 1970-01-01
    • 2011-11-18
    • 1970-01-01
    相关资源
    最近更新 更多