从ViewPager更新片段

我有一个ViewPager Activity 。 我也有一个Dialog ,将检索用户将select的一些项目列表。 现在,我怎么能更新项目应该显示为附加到这个片段的新视图的片段?

这是我的ViewPager的适配器:

 public static class MyAdapter extends FragmentPagerAdapter { public MyAdapter(FragmentManager fm) { super(fm); } @Override public int getCount() { return 1; } @Override public android.support.v4.app.Fragment getItem(int position) { switch (position) { case 0: return new Fragment1(); default: return null; } } } 

现在,这里是Fragment

 public class Fragment1 extends Fragment{ @Override public void onActivityCreated(Bundle savedInstanceState) { // TODO Auto-generated method stub super.onActivityCreated(savedInstanceState); } @Override public void onCreate(Bundle savedInstanceState) { // TODO Auto-generated method stub super.onCreate(savedInstanceState); } @Override public ViewGroup onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { // TODO Auto-generated method stub ViewGroup view = (ViewGroup)inflater.inflate(R.layout.screen1, container, false); } return view; } } 

这是我想用来添加项目到我的Fragment

 private void addItem() { // Instantiate a new "row" view. final ViewGroup[] newViews = new ViewGroup[selectedItems.length]; for(int i = 0; i < selectedItems.length; i++){ newViews[i] = (ViewGroup) LayoutInflater.from(this).inflate( R.layout.animated_layout_item, mContainerView, false); // Set the text in each new row. ((TextView) newViews[i].findViewById(android.R.id.text1)).setText(selectedItems[i]); // Because mContainerView has android:animateLayoutChanges set to true, // adding this view is automatically animated. mContainerView.addView(newViews[i], 0); // Set a click listener for the "X" button in the row that will remove the row. OnClickListener listener = new MyAddItemListener(newViews[i], mContainerView, this); newViews[i].findViewById(R.id.delete_button).setOnClickListener(listener); } } 

从ViewPager更新片段

你需要实现getItemPosition(Object obj)方法。

这个方法在你打电话时被调用

 notifyDataSetChanged() 

在你的ViewPagerAdaper 。 隐含地说,这个方法返回POSITION_UNCHANGED值,这意味着像这样: “片段是它应该是这样的,所以不要改变任何东西。

所以如果你需要更新Fragment,你可以这样做:

  • 始终从getItemPosition()方法返回POSITION_NONE 。 这意味着: “片段必须重新创build”
  • 你可以创build一些update()方法来更新你的Fragment(片段将自己处理更新)

第二种方法的例子:

 public interface Updateable { public void update(); } public class MyFragment extends Fragment implements Updateable { ... public void update() { // do your stuff } } 

而在FragmentPagerAdapter中,你会做这样的事情:

 @Override public int getItemPosition(Object object) { MyFragment f = (MyFragment ) object; if (f != null) { f.update(); } return super.getItemPosition(object); } 

如果你select第一种方法,它可以看起来像:

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

注意:有必要考虑一下你会select哪种方法。

我遇到了一些问题,所以在这种情况下总是避免使用FragmentPagerAdapter并使用FragmentStatePagerAdapter。

它为我工作。 我希望它也能为你工作。

我按照Sajmon的回答执行了一个应用程序演示。 只是为了search这个问题的其他人。

您可以访问GitHub上的源代码

在这里输入图像描述

在你的PagerAdapter覆盖getItemPosition

 @Override public int getItemPosition(Object object) { // POSITION_NONE makes it possible to reload the PagerAdapter return POSITION_NONE; } 

之后添加viewPager.getAdapter()。notifyDataSetChanged(); 这个代码如下所示

 viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() { @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { } @Override public void onPageSelected(int position) { viewPager.getAdapter().notifyDataSetChanged(); } @Override public void onPageScrollStateChanged(int state) { } }); 

应该工作。

接受的答案是不明白的,这就是为什么添加简单的解决scheme。 经过漫长的奋斗寻找工作解

只要通知你的适配器 ,它的工作令人惊叹,

参考代码

  void setAdapter(int position) { PagerAdapter pagerAdapter = new PagerAdapter(getSupportFragmentManager()); viewPager.setAdapter(pagerAdapter); // when notify then set manually current position. viewPager.setCurrentItem(position); pagerAdapter.notifyDataSetChanged(); } 

当您设置适配器并且想要刷新UI时调用此代码。

在您的片段中添加此代码进行刷新

 ((YourActivityName) getContext()).setAdapter(selectedTabPosition); 

使用instanceof投射上下文。

这个代码共享只是帮助寻找解决scheme的目的。

您可以用两种不同的方式更新片段,

第一种方式

像@Sajmon

你需要实现getItemPosition(Object obj)方法。

这个方法在你打电话时被调用

 notifyDataSetChanged() 

你可以在Github中find一个例子,在这篇文章中有更多的信息。

在这里输入图像描述

第二种方式

我在viewpager中更新片段的方法是对instantiateItem setTag()方法中的任何实例化视图使用setTag() instantiateItem()方法。 因此,当您想要更改数据或使需要的视图无效时,可以调用ViewPager上的findViewWithTag()方法来检索先前实例化的视图,并根据需要修改/使用它,而无需删除/创build新视图每次你想更新一些值。

 @Override public Object instantiateItem(ViewGroup container, int position) { Object object = super.instantiateItem(container, position); if (object instanceof Fragment) { Fragment fragment = (Fragment) object; String tag = fragment.getTag(); mFragmentTags.put(position, tag); } return object; } public Fragment getFragment(int position) { Fragment fragment = null; String tag = mFragmentTags.get(position); if (tag != null) { fragment = mFragmentManager.findFragmentByTag(tag); } return fragment; } 

你可以在Github中find一个例子,或者在这篇文章中find更多的信息:

在这里输入图像描述

更新您的片段视图的一个非常简单而有效的解决scheme。 使用setUserVisibleHint()方法。 当片段即将被用户看见时,它将被调用。 在那里你可以更新我们的视图( setText()setVisibility()等)

 @Override public void setUserVisibleHint(boolean isVisibleToUser) { super.setUserVisibleHint(isVisibleToUser); if(isVisibleToUser){ //Write your code to be executed when it is visible to user } } 

它在我的情况下工作。 希望它有帮助!

也许你的方法添加项目到片段应公开 (放置在所需的片段),并应具有相同的types作为selectedItems参数..

这将使其可见的活动,这将有selectedItems数组和瞧…

更好地命名为addItemsFromArray(typeOfSelectedItems[] pSelectedItems)原因名称addItem()是相当不addItemsFromArray(typeOfSelectedItems[] pSelectedItems)

编辑:stackoverflow只是build议类似的话题:) 在这里查看详细的想法实现.. 🙂

很简单,覆盖片段中的方法:

 @Override public void setUserVisibleHint(boolean isVisibleToUser) { super.setUserVisibleHint(isVisibleToUser); if(isVisibleToUser){ actionView(); } else{ //no } } 

1)在你想要更新的片段中创build一个处理程序。

 public static Handler sUpdateHandler; @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); ... sUpdateHandler = new Handler(){ @Override public void handleMessage(Message msg) { super.handleMessage(msg); // call you update method here. } }; } 

2)在活动/片段/对话框中,无论您想要触发更新调用,请获取对该处理程序的引用,并发送消息(告诉您的片段更新)

 // Check if the fragment is visible by checking if the handler is null or not. Handler handler = TaskTabCompletedFragment.sUpdateHandler; if (handler != null) { handler.obtainMessage().sendToTarget(); }