• 关于fragment+viewpager的优化


    上次写了一个问答项目,用的fragment+viewpager架构,后来发现,划了几次之后,再划回来,会重新加载布局,重新获取数据,这样整个程序和卡,并且占用太多的网络资源。

    当时的解决办法是,自己重写view,用最基本的Basepageradapder,算是不是很优雅的解决了问题。

    当时知道是重新调用onCreateView方法原因,但是没有好的解决办法,现在知道了,这里记载一下。

    我实验了viewpager加载四个fragment:

    第一次进入的时候:

    1
    2
    3
    4
    5
    6
    <span style="font-size:18px;">03-01 13:50:16.151  22667-22667/com.graypn.modelproject I/onCreate1﹕ onCreate
    03-01 13:50:16.151  22667-22667/com.graypn.modelproject I/onCreateView1﹕ onCreateView
    03-01 13:50:16.161  22667-22667/com.graypn.modelproject I/onActivityCreated1﹕ onActivityCreated
    03-01 13:50:16.161  22667-22667/com.graypn.modelproject I/onCreate2﹕ onCreate
    03-01 13:50:16.161  22667-22667/com.graypn.modelproject I/onCreateView2﹕ onCreateView
    03-01 13:50:16.161  22667-22667/com.graypn.modelproject I/onActivityCreated2﹕ onActivityCreated</span>

    往右滑动到第二个界面:

    1
    2
    3
    <span style="font-size:18px;">03-01 13:51:22.391  22667-22667/com.graypn.modelproject I/onCreate3﹕ onCreate
    03-01 13:51:22.391  22667-22667/com.graypn.modelproject I/onCreateView3﹕ onCreateView
    03-01 13:51:22.401  22667-22667/com.graypn.modelproject I/onActivityCreated3﹕ onActivityCreated</span>

    往右滑动到第三个界面:

    1
    2
    3
    4
    03-01 13:55:24.351  24165-24165/com.graypn.modelproject I/onDestroyView1﹕ onDestroyView
    03-01 13:55:24.351  24165-24165/com.graypn.modelproject I/onCreate4﹕ onCreate
    03-01 13:55:24.351  24165-24165/com.graypn.modelproject I/onCreateView4﹕ onCreateView
    03-01 13:55:24.361  24165-24165/com.graypn.modelproject I/onActivityCreated4﹕ onActivityCreated

    往右滑动到第四个界面:

    1
    03-01 13:56:22.021  24165-24165/com.graypn.modelproject I/onDestroyView2﹕ onDestroyView

    往左划到第三个界面:

    1
    2
    03-01 13:58:09.541  24165-24165/com.graypn.modelproject I/onCreateView2﹕ onCreateView
    03-01 13:58:09.541  24165-24165/com.graypn.modelproject I/onActivityCreated2﹕ onActivityCreated

    结论:viewpager会加载和当前页面相连的两个fragment,会销毁相邻第三个页面的view,再次调用是会重新oncreateview和onactivityreate。

    我们需要优化自己的fragment,如下时我优化后的类:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    <span style="font-size:18px;">/**
     * 提供了fragment的封装后基类,提供context给子类使用
     *
     * @author Graypn
     */
    public abstract class BaseFragment extends Fragment {
     
        //根部view
        private View rootView;
        protected Context context;
        private Boolean hasInitData = false;
     
        @Override
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            context = getActivity();
        }
     
        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container,
                                 Bundle savedInstanceState) {
            if (rootView == null) {
                rootView = initView(inflater);
            }
            return rootView;
        }
     
        @Override
        public void onActivityCreated(Bundle savedInstanceState) {
            super.onActivityCreated(savedInstanceState);
            if (!hasInitData) {
                initData();
                hasInitData = true;
            }
        }
     
        @Override
        public void onDestroyView() {
            super.onDestroyView();
            ((ViewGroup) rootView.getParent()).removeView(rootView);
        }
     
        /**
         * 子类实现初始化View操作
         */
        protected abstract View initView(LayoutInflater inflater);
     
        /**
         * 子类实现初始化数据操作(子类自己调用)
         */
        public abstract void initData();
     
        /**
         * 封装从网络下载数据
         */
        protected void loadData(HttpRequest.HttpMethod method, String url,
                                RequestParams params, RequestCallBack<string> callback) {
            if (0 == NetUtils.isNetworkAvailable(getActivity())) {
                new CustomToast(getActivity(), 无网络,请检查网络连接!, 0).show();
            } else {
                NetUtils.loadData(method, url, params, callback);
            }
        }
     
    }</string></span>


    加入rootView,缓存加载后的view,如果有就不重新加载数据。

    加入判断是否已经加载数据完成的标志变量,如果已经加载了数据,就不重新加载数据。

    算是优雅的解决了优化的问题,希望能帮到有同样问题的同学。

  • 相关阅读:
    QtDBus快速入门
    论Qt容器与STL
    JS中的!=、== 、!==、===的用法和区别
    JS操作JSON总结
    select2使用方法总结
    Entity Framework插入数据报错:Validation failed for one or more entities. See 'EntityValidationErrors' property for more details.
    Windows登录类型及安全日志解析
    <script type="text/html"></script> js模版使用
    在 C# 中,(int) ,Int32.Parse() 和 Convert.toInt32() 三种方法的区别
    关于session,cookie,Cache
  • 原文地址:https://www.cnblogs.com/likeju/p/4826366.html
Copyright © 2020-2023  润新知