onPageSelected不适用于第一页

我的寻呼机适配器(扩展PagerAdepter)中有一个文本视图。 我用MainActivity的onPageSelected更新这个textview。 其位置> 0的更新文本视图,但起始页(位置0)不会在启动时更新。 当我向前滑动然后向后滑动; 它设置位置0的值,但是我不能将值设置为ON START。 如何设置星级页面的值?

public void onPageSelected(int position) { switch (position) { case 0: PagerAdapter.tv.setText("value"); // => doesnt work on start break; default: PagerAdapter.tv.setText("value"); break; } } 

完整代码:

 public class QuizStart extends SlidingFragmentActivity { @Override protected void onCreate(final Bundle savedInstanceState) { super.onCreate(savedInstanceState); this.setContentView(R.layout.activity_main); mPager = (ViewPager)findViewById(R.id.pager); QuestionPagerAdapter mAdapter = new QuestionPagerAdapter(); mPager.setAdapter(mAdapter); QuizStart.onPageSelected(0); mPager.setOnPageChangeListener(new OnPageChangeListener() { @Override public void onPageScrollStateChanged(int arg0) { } @Override public void onPageScrolled(int arg0, float arg1, int arg2) { } @Override public void onPageSelected(int position) { switch (position) { case 0: PagerAdapter.tv.setText("value"); // => doesnt work on start break; default: PagerAdapter.tv.setText("value"); break; } } }); } } 

您可以在创buildOnPageChangeListener以设置起始状态时手动调用onPageSelected(0)

 OnPageChangeListener pageChangeListener = new OnPageChangeListener() { @Override public void onPageScrollStateChanged(int arg0) { } @Override public void onPageScrolled(int arg0, float arg1, int arg2) { } @Override public void onPageSelected(int position) { switch (position) { case 0: QuizStart.next.setText(getmycurrentpage()+""); break; default: QuizStart.next.setText(getmycurrentpage()+""); break; } } }); mPager.setOnPageChangeListener(pageChangeListener); // do this in a runnable to make sure the viewPager's views are already instantiated before triggering the onPageSelected call mPager.post(new Runnable() { @Override public void run() { pageChangeListener .onPageSelected(viewPager.getCurrentItem()); } }); 

编辑

现在它不会像@ metemet06指出的那样得到Null Pointer exception

对我来说,下一个代码

  viewPager.addOnPageChangeListener(myOnPageChangeListener); 

  ViewPager.OnPageChangeListener myOnPageChangeListener = new ViewPager.OnPageChangeListener() { //declare key Boolean first = true; @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { if (first && positionOffset == 0 && positionOffsetPixels == 0){ onPageSelected(0); first = false; } } @Override public void onPageSelected(int position) { //do what need } @Override public void onPageScrollStateChanged(int state) { } }; 

我的解决scheme是扩展寻呼机适配器,并在其中创build一个接口。 然后让适配器在创build适配器后只调用一次接口。 在接口callback里,你可以调用onPageChanged方法而不会有nullpointerexception。 将此类添加到您的项目中,并从中扩展您的适配器。 在将适配器设置为viewpager之前,不要忘记将监听器设置为适配器。 适配器类如下:

 public abstract class ExtendedPagerAdapter extends FragmentPagerAdapter { private boolean instantiated; private AdapterListener adapterListener; public interface AdapterListener { void onAdapterInstantiated(); } public ExtendedPagerAdapter(FragmentManager fragmentManager) { this(fragmentManager, null); } public ExtendedPagerAdapter(FragmentManager fragmentManager, AdapterListener adapterListener) { super(fragmentManager); this.adapterListener = adapterListener; instantiated = false; } @Override public void finishUpdate(ViewGroup container) { super.finishUpdate(container); if (!instantiated) { instantiated = true; if (adapterListener != null) { adapterListener.onAdapterInstantiated(); } } } public void setAdapterInstantiatedListener(AdapterListener adapterListener) { this.adapterListener = adapterListener; } } 

我通过添加应该为我的活动的onCreate()方法中的第一个页面执行的代码解决了我的应用程序中的问题。

它不是最漂亮的黑客,并涉及一些冗余的代码,但因为我只想加载一些文本数据,当页面正在改变这是最简单的方法来做我的情况。

手动调用onPageSelected()会导致NullPointerExceptions,只是在上面的其他注释中描述的das。

在我看来,你真正想要做的是重写getPageTitle() ,然后,在别的地方抓取该页面标题并将其设置为TextView的文本。

这样,当你初始化你的活动,初始化PagerAdapter并调用getTitle(0) 。 这将为您获得页面0的标题。现在在活动的文本视图中进行设置。 之后,只要调用getTitle(newPosition)并更新TextView就可以了。

您可能使用一些AsyncTasks加载数据集,并且很难确定哪个任务将是最后一个完成。 只有在完成最后一个任务后,当整个数据集完成后,才可以调用OnPageSelected,因为它在整个数据集的UI上执行刷新。

而不是在第一次加载页面时手动调用OnPageSelected函数,而是逐步build立“正常”UI。 稍后,当用户更改页面时,数据集应该是完整的,并保存在OnPageSelected函数中进行更新。

因为我做了什么build议在这里,它没有工作,我会发布什么工作给我join实例化函数onPageScrolled,如下所示:

  @Override public void onPageScrolled(int arg0, float arg1, int arg2) { adapter.closeText(arg0, viewPager); } 

可能的原因是onPagesScrolled在android任务pipe理器的下方被激活,所以我们可以防止页面膨胀的不必要的情况,并且跳过监听器附件到视图。

这个代码适合我。 首先初始化pagechange监听器。 在setCurrentItem之后。

 viewPager.setAdapter(adapter); viewPager.setOffscreenPageLimit(1); final ViewPager.OnPageChangeListener listener = new ViewPager.OnPageChangeListener() { @Override public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { } @Override public void onPageSelected(int position) { } @Override public void onPageScrollStateChanged(int state) { } }; viewPager.addOnPageChangeListener(listener); viewPager.setCurrentItem(position); 

其实我基于这个答案find了一个好方法。

问题是当侦听器安装时, ViewPager没有被完全加载,第一个页面被调用,但是ViewPager内部的ViewPager还没有被完全初始化。

为了解决这个问题,我只保留一个variables来知道第一页是否被调用:

 private boolean mFirstPageCalled = false; 

然后在听众:

 @Override public void onPageSelected(int position) { if(mFirstPageCalled) { // Do your thing } else { mFirstPageCalled = true; } } 

最后要做的是处理错过的第一页,这可以在ViewPager完全创build完成后完成:

  mViewPager.post(new Runnable(){ @Override public void run() { // Do your thing } }); 

在我的情况下,我只是回到现在的片段显示和工作:

 Fragment currentFragment = mPagerAdapter.instantiateItem(mViewPager, mViewPager.getCurrentItem()); currentFragment.customAction(); 

post方法只被调用一次,所以处理首页的情况非常完美。

我的解决scheme是一个扩展ViewPager

 class MyViewPager extends ViewPager { private List<OnPageChangeListener> _Listeners = new ArrayList<>(); public MyViewPager(Context context) { super(context); } public MyViewPager(Context context, AttributeSet attrs) { super(context, attrs); } @Override public void addOnPageChangeListener(OnPageChangeListener listener) { super.addOnPageChangeListener(listener); _Listeners.add(listener); } @Override public void removeOnPageChangeListener(OnPageChangeListener listener) { super.removeOnPageChangeListener(listener); _Listeners.remove(listener); } @Override public void setCurrentItem(final int item) { if (item != getCurrentItem()) { super.setCurrentItem(item); } else { post(new Runnable() { @Override public void run() { dispatchOnPageSelected(item); } }); } } private void dispatchOnPageSelected(int position) { for (int i = 0, size = _Listeners.size(); i < size; i++) { OnPageChangeListener listener = _Listeners.get(i); if (listener != null) { listener.onPageSelected(position); } } } }