ViewPager Shows Wrong Content after Removing a Page

400 views Asked by At

I have created a ViewPager implementation with FragmentStatePagerAdapter to let the user of my app browse through and edit a potentially large number of records. The parent activity's menu includes a delete button, which allows the user to remove the currently shown fragment. Fragments include quasi static (e.g. TextView ) as well es directly editible data (e.g. EditText). Data is saved upon editing (not shown here for brevity).

What happens now when I delete a page is that the next record is shown, which is intended. The TextView show correctly but the EditText of the current page shows the corresponding value of the deleted page, and also the next page's value is taken from the wrong record.

How can I get the ViewPager to also show the EditText views correctly?

For instance, after removing page 3 with content 3, I get the following:

enter image description here

Below is the code for the Activity, the FragmentStatePagerAdapter, and the Fragment.

Activity:

public class ViewPagerActivity extends AppCompatActivity {

    private ViewPagerAdapter mViewPagerAdapter;
    private ViewPager mViewPager;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_view_pager);

        mViewPager = (ViewPager) findViewById(R.id.viewPager);

        mViewPagerAdapter = new ViewPagerAdapter(getSupportFragmentManager());
        mViewPager.setAdapter(mViewPagerAdapter);
        mViewPager.setCurrentItem(0);
    }

    public boolean onCreateOptionsMenu(Menu menu) {
        super.onCreateOptionsMenu(menu);

        getMenuInflater().inflate(R.menu.menu_view_pager, menu);
        return true;
    }

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        super.onOptionsItemSelected(item);

        switch (item.getItemId()) {
            case R.id.action_delete:
                deleteItem();
                return true;
        }
        return super.onOptionsItemSelected(item);
    }

    private void deleteItem() {
        mViewPagerAdapter.removeItem(this, mViewPager.getCurrentItem());
        if (mViewPagerAdapter.getCount() == 0) {
            finish();
        }
    }
}

Adapter:

class ViewPagerAdapter extends FragmentStatePagerAdapter {

    private List<PageContent> mPageContents;

    ViewPagerAdapter(FragmentManager fm) {
        super(fm);
        mPageContents = new ArrayList<>();
        mPageContents.add(new PageContent("Page 1", "Detail 1"));
        mPageContents.add(new PageContent("Page 2", "Detail 2"));
        mPageContents.add(new PageContent("Page 3", "Detail 3"));
        mPageContents.add(new PageContent("Page 4", "Detail 4"));
        mPageContents.add(new PageContent("Page 5", "Detail 5"));
        mPageContents.add(new PageContent("Page 6", "Detail 6"));
    }

    @Override
    public int getCount() {
        return mPageContents.size();
    }

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

    @Override
    public Fragment getItem(int position) {
        PageContent pageContent = mPageContents.get(position);
        return PagerFragment.newInstance(pageContent.getTitle(), pageContent.getDescription());
    }

    void removeItem(AppCompatActivity activity, int position) {
        mPageContents.remove(position);
        notifyDataSetChanged();
        if (mPageContents.size() == 0) {
            activity.finish();
        }
    }
}


class PageContent {

    private String mTitle;
    String getTitle() { return mTitle; }
    private String mDescription;
    String getDescription() { return mDescription; }

    PageContent(String title, String content) {
        mTitle = title;
        mDescription = content;
    }
}

Fragment:

public class PagerFragment extends Fragment {

    private String mTitle;
    private String mDetail;
    private static final String ARG_TITLE = "title";
    private static final String ARG_DETAIL = "detail";

    public PagerFragment() { }

    public static PagerFragment newInstance(String title, String detail) {
        PagerFragment fragment = new PagerFragment();
        Bundle args = new Bundle();
        args.putString(ARG_TITLE, title);
        args.putString(ARG_DETAIL, detail);
        fragment.setArguments(args);
        return fragment;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        mTitle = getArguments().getString(ARG_TITLE);
        mDetail = getArguments().getString(ARG_DETAIL);
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_pager, container, false);

        TextView titleView = (TextView) view.findViewById(R.id.title);
        EditText detailView = (EditText) view.findViewById(R.id.detail);

        titleView.setText(mTitle);
        detailView.setText(mDetail);

        return view;
    }
}
1

There are 1 answers

0
iamkaan On BEST ANSWER

Try calling setText methods in onResume method in your PagerFragment. Found the answer here: https://stackoverflow.com/a/12987279/2121682. Not sure why or how, but it worked when I tried it on your code.

public class PagerFragment extends Fragment {

    private String mTitle;
    private String mDetail;
    private static final String ARG_TITLE = "title";
    private static final String ARG_DETAIL = "detail";

    TextView titleView;
    EditText detailView;

    public PagerFragment() {
    }

    public static PagerFragment newInstance(String title, String detail) {
        PagerFragment fragment = new PagerFragment();
        Bundle args = new Bundle();
        args.putString(ARG_TITLE, title);
        args.putString(ARG_DETAIL, detail);
        fragment.setArguments(args);
        return fragment;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        mTitle = getArguments().getString(ARG_TITLE);
        mDetail = getArguments().getString(ARG_DETAIL);
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.item_pager, container, false);

        titleView = (TextView) view.findViewById(R.id.text);
        detailView = (EditText) view.findViewById(R.id.edit);

        return view;
    }

    @Override
    public void onResume() {
        super.onResume();

        titleView.setText(mTitle);
        detailView.setText(mDetail);
    }
}