ViewPager问题

时间:2015-11-30 09:41:55

标签: android android-fragments android-viewpager

我想创建这样的东西:

enter image description here

ViewPager附加到具有2个片段的适配器。一个列出即将到来的订单,另一个列出过去的订单。

因此上面显示的图像有一个主片段,它承载着ViewPager,并且适配器创建了2个片段作为主片段的子片。

为简单起见,我将主片段称为“父片段”,并将适配器提供的两个片段称为“子片段”。

创建或恢复父片段后,它必须从服务器获取数据列表并将其传递给两个子片段(子片段将处理数据列表并显示必要的数据)。两个子片段都有一个listView,每个listView行项都是可点击的。

现在,在将ViewPager连接到适配器之前,必须将父片段提取的数据传递给子片段。所以我没有在父片段的onCreate方法中将适配器附加到ViewPager,而是在获取数据列表后,在获取数据后,我将适配器附加到异步任务的onPostExecute方法中的ViewPager。

第一次工作正常,但是一旦我点击子片段的listView行项目然后按后退按钮,就不会调用适配器的getItem()方法,而是调用子片段的onResume方法甚至在从服务器获取数据之前调用。

所以我想android框架会记住子片段已经创建,并且不会再次重新创建它们。

如何确保在父片段中从服务器获取数据后才创建/调用子片段?

为了清晰起见,我正在添加一些代码。

BookingHistory.java(父片段)

    public class BookingHistory extends android.support.v4.app.Fragment {
    ViewPager mPager;
    SlidingTabLayout mTabs;
    Toolbar toolBar;
    View view;

    private ProgressDialog progress;
    private OrderTask mOrderTask = null;
    UserFunctions userFunctions = null;
    OrderFunctions orderFunctions = null;
    private BookingHistoryListener mListener;
    private List<Order> mOrderList;

    PlacedOrders upcomingOrders;
    PlacedOrders pastOrders;

    public BookingHistory() {
        // Required empty public constructor
    }

    @Override
    public void onResume() {
        super.onResume();
        mOrderList = null;
        mPager = null;
        mTabs = null;
        upcomingOrders = null;
        pastOrders = null;
        progress = new ProgressDialog(getActivity());
        fetchOrders();
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {

        view = inflater.inflate(R.layout.fragment_booking_history, container, false);
        toolBar = (Toolbar) view.findViewById(R.id.toolbar_s);
        if (toolBar != null) {
            TextView tv = (TextView) view.findViewById(R.id.toolbar_title);
            toolBar.setTitle("");
            tv.setText("History");
        }
        return view;
    }

    class MyPagerAdapter extends FragmentPagerAdapter {
        String tabs[] = {"Upcoming", "Past"};

        public MyPagerAdapter(android.support.v4.app.FragmentManager fm) {
            super(fm);
        }

        @Override
        public android.support.v4.app.Fragment getItem(int position) {
            if (position == 0) {
                upcomingOrders = PlacedOrders.newInstance(Constants.DATE_TODAY_FUTURE);
                upcomingOrders.getOrderList(mOrderList);
                return upcomingOrders;
            } else {
                pastOrders = PlacedOrders.newInstance(Constants.DATE_PAST);
                pastOrders.getOrderList(mOrderList);
                return pastOrders;
            }
        }

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

        @Override
        public int getCount() {
            return 2;
        }
    }

    public void fetchOrders() {
        if (mOrderTask != null) {
            return;
        }
        progress.show();
        mOrderTask = new OrderTask(getActivity());
        mOrderTask.execute((Void) null);
    }

    public class OrderTask extends AsyncTask<Void, Void, Boolean> {

        private final Activity mActivity;

        OrderTask(Activity activity) {
            mActivity = activity;
        }

        @Override
        protected Boolean doInBackground(Void... params) {
            userFunctions = new UserFunctions();
            orderFunctions = new OrderFunctions();
            return orderFunctions.getList(userFunctions.getToken(mActivity));
        }

        @Override
        protected void onPostExecute(final Boolean success) {
            mOrderTask = null;
            progress.dismiss();
            if (success) {
                mOrderList = UserProfile.getOrders();
                //attaching the view pager to adapter here!
                mPager = (ViewPager) view.findViewById(R.id.pager);
                mTabs = (SlidingTabLayout) view.findViewById(R.id.sliding_tabs);
                mTabs.setDistributeEvenly(true);
                mTabs.setCustomTabColorizer(new SlidingTabLayout.TabColorizer() {
                    @Override
                    public int getIndicatorColor(int position) {
                        return getResources().getColor(R.color.white);
                    }
                });
                mPager.setAdapter(new MyPagerAdapter(getChildFragmentManager()));
                mTabs.setViewPager(mPager);
            } else {
                //Error handling stuff
            }
        }
    }
}

PlacedOrders.java(儿童片段)

    public class PlacedOrders extends android.support.v4.app.Fragment {

    private static String flag;
    private int dateFlag;
    private PlacedOrdersListener mListener;
    UserFunctions userFunctions = null;
    OrderFunctions orderFunctions = null;
    private PlacedOrdersAdapter ordersAdapter;
    private ProgressDialog progress;
    private List<Order> mOrderList;
    private List<Order> mPendingOrderList;
    private List<Order> mCompletedOrderList;

    public static PlacedOrders newInstance(int date) {
        PlacedOrders fragment = new PlacedOrders();
        Bundle args = new Bundle();
        args.putInt(flag, date);
        fragment.setArguments(args);
        return fragment;
    }

    public void getOrderList(List<Order> orderList) {
        this.mOrderList = orderList;
    }

    public PlacedOrders() {
        // Required empty public constructor
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        if (getArguments() != null) {
            dateFlag = getArguments().getInt(flag);
        }
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        mPendingOrderList = new ArrayList<Order>();
        mCompletedOrderList = new ArrayList<Order>();
        return inflater.inflate(R.layout.fragment_placed_orders, container, false);
    }

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

    private void displayOrders() {
        if (isVisible() && (mOrderList != null)) {
            mPendingOrderList.clear();
            mCompletedOrderList.clear();
            ListView listViewOrder = (ListView) getView().findViewById(R.id.orderList);
            if(dateFlag == Constants.DATE_TODAY_FUTURE) {
                for(int i = 0; i < mOrderList.size(); i++) {
                    String status = mOrderList.get(i).status;
                    if(status.equals("PENDING") || status.equals("PROCESSING")) {
                        mPendingOrderList.add(mOrderList.get(i));
                        ordersAdapter = new PlacedOrdersAdapter(mPendingOrderList, getActivity().getLayoutInflater());
                        listViewOrder.setAdapter(ordersAdapter);
                    }
                }
            }
            else if(dateFlag == Constants.DATE_PAST) {
                for(int i = 0; i < mOrderList.size(); i++) {
                    String status = mOrderList.get(i).status;
                    if(status.equals("COMPLETE")) {
                        mCompletedOrderList.add(mOrderList.get(i));
                        ordersAdapter = new PlacedOrdersAdapter(mCompletedOrderList, getActivity().getLayoutInflater());
                        listViewOrder.setAdapter(ordersAdapter);
                    }
                }
            }

            listViewOrder.setOnItemClickListener(new AdapterView.OnItemClickListener() {
               //Display a new fragment on clicking
            });
        }
    }

}

1 个答案:

答案 0 :(得分:0)

我有同样的问题,这是我的解决方案: 在onViewCreated()方法的容器片段(包含制表符的片段)中,我创建了startFetch()方法:

@Override
    public void onViewCreated(View v, Bundle savedInstanceState) {
        super.onViewCreated(v, savedInstanceState);
        mViewPager = (ViewPager) v.findViewById(R.id.home_tab_pager);
        mTabsHost= (TabLayout) getActivity().findViewById(R.id.appTabs);
        startFetch();
    }

然后在startFetch方法中我使用Volley请求并在onResponse方法中更新数据然后添加标签:

public void startFetch(){
        //Create volley request
        String url = BuildConfig.API_GET_CATEGORIES;
        final RequestQueue queue = VolleyService.getInstance(this.getContext()).getRequestQueue();
        StringRequest request = new StringRequest(url, new Response.Listener<String>() {

            @Override
            public void onResponse(String response) {
                // we got the response, now our job is to handle it
                try {
                    updateCategoryData(response);
                } catch (RemoteException | OperationApplicationException e) {
                    e.printStackTrace();
                }
            }
        }, new Response.ErrorListener() {

            @Override
            public void onErrorResponse(VolleyError error) {
                //something happened, treat the error.
                Log.e("ErrorFETCH", error.networkResponse.toString());
            }
        });

        queue.add(request);
    }

我的udpateCategory()方法:

public void updateCategoryData(final String stream) throws RemoteException, OperationApplicationException {
//Update the data to SQLITE
setupTabs();
}

我的setupTabs()方法:

public void setUpTabs(){
        ArrayList<Category> categories = new ArrayList<>();
        Cursor data = getActivity().getContentResolver().query(
                Category.Entry.CONTENT_URI, // URI
                Category.PROJECTION,                // Projection
                Category.Entry.COLUMN_NAME_PARENT_ID + " = ?",   // Selection
                new String[]{"0"},                          // Selection args
                null);

        if (data != null) {
            while(data.moveToNext()){
                categories.add(new Category(data));
            }
        }

        TabsPagerAdapter mAdapter = new TabsPagerAdapter(getActivity().getSupportFragmentManager(), this.getActivity(), categories);
        mViewPager.setAdapter(mAdapter);


        mTabsHost.setupWithViewPager(mViewPager);
    }