fragment切换_fragment切换闪退 - CSDN
精华内容
参与话题
  • 我们都知道fragment切换有两种方式: 1. replace方式 transaction.replace(R.id.content, fragment1); 2. add-hide-show方式 transaction.add(R.id.content, fragment1); transaction.hide(fragment2); ...

    我们都知道fragment切换有两种方式:
    1. replace方式
    transaction.replace(R.id.content, fragment1);
    2. add-hide-show方式
    transaction.add(R.id.content, fragment1); transaction.hide(fragment2); transaction.show(fragment1);

    来看一下使用add切换时候的生命周期:
    载入Fragment1
    Fragment1 onCreate
    Fragment1 onCreateView
    Fragment1 onStart
    Fragment1 onResume
    用以下代码切到Fragment2:

    FragmentTransaction ft = getFragmentManager().beginTransaction();
            ft.hide(fragment1);
            ft.add(R.id.simple_fragment, fragment2);
            ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
            ft.commit();


    Fragment1不走任何生命周期,但会调onHiddenChanged方法
    Fragment2 onCreate
    Fragment2 onCreateView
    Fragment2 onStart
    Fragment2 onResume
    回到Fragment1,Hide Fragment2:


    FragmentTransaction ft = getFragmentManager().beginTransaction();
            if(!fragment1.isAdd()){
                ft.add(R.id.simple_fragment, fragment1);
            }else{
                ft.show(fragment1);
            }
            ft.hide(fragment2);
            ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
            ft.commit();


    Fragment1还是不走任何生命周期,调onHiddenChanged方法
    Fragment2 onPause
    Fragment2 onStop
    Fragment2 onDestoryView
    Fragment2 onDestory
    用这种方法切换,Fragment在隐藏时并不会走onDestoryView,所以显示时也不会走onCreateView,所有View都一直保存在内存中。

    用replace方法:
    载入Fragment1生命周期与上面相同:
    Fragment1 onCreate
    Fragment1 onCreateView
    Fragment1 onStart
    Fragment1 onResume
    切到Fragment2:


    FragmentTransaction ft = getFragmentManager().beginTransaction();
            ft.replace(R.id.simple_fragment, fragment2);
            ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
            ft.commit();


    这次的Fragment1走生命周期了
    Fragment1 onPause
    Fragment1 onStop
    Fragment1 onDestoryView
    Fragment1 onDestory
    Fragment2 onCreate
    Fragment2 onCreateView
    Fragment2 onStart
    Fragment2 onResume
    可以看到,Fragment1走了onDestory,被完全回收了!
    再切回到Fragment1


    FragmentTransaction ft = getFragmentManager().beginTransaction();
            ft.replace(R.id.simple_fragment, fragment1);
            ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_OPEN);
            ft.commit();


    Fragment1 onCreate
    Fragment1 onCreateView
    Fragment1 onStart
    Fragment1 onResume
    Fragment2 onPause
    Fragment2 onStop
    Fragment2 onDestoryView
    Fragment2 onDestory
    Fragment1因为已经被回收,又走onCreate,Fragment2被回收。

    展开全文
  • Fragment切换

    2018-11-06 15:14:05
    Fragment使用率非常大,最常见的就是APP首页,和Activity组成的首页,例如微信主界面,今天就来看一看Fragment切换是如何操作的。 布局文件: 看微信的主页面,实则就是一个Activity,通过下方的几个按钮进行...

    Fragment使用率非常大,最常见的就是APP首页,和Activity组成的首页,例如微信主界面,今天就来看一看Fragment切换是如何操作的。

    布局文件:

    看微信的主页面,实则就是一个Activity,通过下方的几个按钮进行fragment的切换,首先我们现在写一下Activity的布局,既然要用到Fragment,我们在布局中就需要一个FrameLayout来装载Fragment,然后在下方写几个按钮,这里我们用RadioButton:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">
    
        <FrameLayout
            android:id="@+id/fl"
            android:layout_width="match_parent"
            android:layout_height="0dp"
            android:layout_weight="1" />
    
        <RadioGroup
            android:id="@+id/rg"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="horizontal">
    
            <RadioButton
                android:id="@+id/btn1"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_weight="1"
                android:button="@null"
                android:checked="true"
                android:drawablePadding="6dp"
                android:drawableTop="@drawable/selector_discovery_btn"
                android:gravity="center"
                android:text="fragment1"
                android:textColor="#333333" />
    
            <RadioButton
                android:id="@+id/btn2"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_weight="1"
                android:button="@null"
                android:drawablePadding="6dp"
                android:drawableTop="@drawable/selector_insight_btn"
                android:gravity="center"
                android:text="fragment2"
                android:textColor="#333333" />
    
            <RadioButton
                android:id="@+id/btn3"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_weight="1"
                android:button="@null"
                android:drawablePadding="6dp"
                android:drawableTop="@drawable/selector_mentions_btn"
                android:gravity="center"
                android:text="fragment3" />
        </RadioGroup>
    
    
    </LinearLayout>  

    代码中,RadioGroup控件里面有很多重复代码,可以写到style.xml文件中统一引用,这里就不做介绍了,可以看我之前的博文。

    drawableTop中我们引用了一个自己写的XML文件,目的是实现当我们选中其中一个按钮时,这个按钮高亮,其他按钮变灰。这里需要提供两张图片,一个高亮,一个灰的图片来写,我贴出代码,大家可以看一看:

    <?xml version="1.0" encoding="utf-8"?>
    <selector xmlns:android="http://schemas.android.com/apk/res/android">
        <item android:drawable="@drawable/ic_discovery_pressed" android:state_checked="true" />
        <item android:drawable="@drawable/ic_discovery_normal" android:state_checked="false" />
    </selector>

    OK ,布局文件写完了,我们还需要三个Fragment:

    public class Fragment1 extends Fragment {
        @Nullable
        @Override
        public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
            return inflater.inflate(R.layout.fragment_fragment1,container,false);
        }
    }

     

    public class Fragment2 extends Fragment {
        @Nullable
        @Override
        public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
            return inflater.inflate(R.layout.fragment_fragment2, container, false);
        }
    }
    public class Fragment3 extends Fragment {
        @Nullable
        @Override
        public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
            return inflater.inflate(R.layout.fragment_fragment3, container, false);
        }
    }

    OK,到现在所有准备工作都差不多了,然后我们开始在Activity中来切换这三个Fragment:

    package sound.zcj.myapplication;
    
    import android.support.v4.app.Fragment;
    import android.support.v4.app.FragmentTransaction;
    import android.support.v7.app.AppCompatActivity;
    import android.os.Bundle;
    import android.widget.FrameLayout;
    import android.widget.RadioGroup;
    
    import java.util.ArrayList;
    import java.util.List;
    
    public class MainActivity extends AppCompatActivity implements RadioGroup.OnCheckedChangeListener {
        private RadioGroup rg;
        private FrameLayout fl;
        //声明三个Fragment
        private Fragment1 fragment1;
        private Fragment2 fragment2;
        private Fragment3 fragment3;
        //实例化一个Fragment用来记录当前展示在眼前的Fragment
        private Fragment currentFragment = new Fragment();
        //用来装三个Fragment的list
        private List<Fragment> fragments = new ArrayList<>();
        private int position = 0;//记录当前fragment索引位置
        //记录当前显示的Fragment的position的key值
        private static final String CURRENT_FRAGMENT = "STATE_FRAGMENT_SHOW";
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            fl = findViewById(R.id.fl);
            //通过ID找到RadioGroup
            rg = findViewById(R.id.rg);
            //当内存重启时,获取我们保存的索引下标position
            if (savedInstanceState != null) {
                position = savedInstanceState.getInt(CURRENT_FRAGMENT, 0);
                fl.removeAllViews();
            }
            //实现RadioGroup监听
            rg.setOnCheckedChangeListener(this);
            //初始化Fragment并添加到list中
            initFragment();
            //展示Fragment
            showFragment(position);
        }
    
        /**
         * 初始化Fragment
         */
        private void initFragment() {
            fragment1 = new Fragment1();
            fragment2 = new Fragment2();
            fragment3 = new Fragment3();
            fragments.add(fragment1);
            fragments.add(fragment2);
            fragments.add(fragment3);
        }
    
        /**
         * @param position 展示Fragment
         */
        private void showFragment(int position) {
            //获取FragmentTransaction
            FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
            if (fragments.get(position).isAdded()) {
                //如果需要展示出的这个Fragment是被添加过的,那么直接隐藏当前Fragment,展示这个Fragment
                transaction.hide(currentFragment).show(fragments.get(position));
            } else {
                //如果需要展示的这个Fragment没有被添加过,那么隐藏当前Fragmnet并且添加这个Fragment
                transaction.hide(currentFragment).add(R.id.fl, fragments.get(position), "" + position);//第三个参数给添加的fragment增加一个标识
            }
            //把这个Fragment设置为当前Fragment
            currentFragment = fragments.get(position);
            //提交
            transaction.commit();
        }
    
        @Override
        public void onCheckedChanged(RadioGroup group, int checkedId) {
            switch (checkedId) {
                //这里position的值与fragments对应
                case R.id.btn1:
                    position = 0;
                    break;
                case R.id.btn2:
                    position = 1;
                    break;
                case R.id.btn3:
                    position = 2;
                    break;
            }
            //展示Fragment
            showFragment(position);
        }
    
        @Override
        protected void onSaveInstanceState(Bundle outState) {
            //保存当前fragment的position
            outState.putInt(CURRENT_FRAGMENT, position);
            super.onSaveInstanceState(outState);
        }
    }
    

    代码中的注释很详细,大家可以看一下,需要提一点的是,重写onSaveInstanceState()方法保存position的目的是为了防止fragment重叠出现。

    展开全文
  • Android 界面(Fragment切换

    千次阅读 2018-10-12 13:59:00
    1.声明 private FragmentManager fManager;//管理Fragment界面 2.初始化 fManager = getSupportFragmentManager();... * Fragment切换 * * @param index */ private void setChoiceItem(int...

    1.声明

    private FragmentManager fManager;//管理Fragment界面
    

    2.初始化

    fManager = getSupportFragmentManager();
    

    3.切换代码

    	/**
         * Fragment切换
         *
         * @param index
         */
        private void setChoiceItem(int index) {
            FragmentTransaction transaction = fManager.beginTransaction();
            clearChoice();
            hideFragments(transaction);
            switch (index) {
                case 0:
                    img_home.setBackgroundResource(R.drawable.home_select);
                    if (home == null) {
                        home = new HomeFragment();
                        transaction.add(R.id.main_frame_layout, home);
                    } else {
                        transaction.show(home);
                    }
    
                    break;
    
                case 1:
                    img_message.setBackgroundResource(R.drawable.message_select);
                    if (message == null) {
                        message = new MessageFragment();
                        transaction.add(R.id.main_frame_layout, message);
                    } else {
                        transaction.show(message);
                    }
                    break;
                case 2:
                    img_attention.setBackgroundResource(R.drawable.attention_select);
                    if (attention == null) {
                        attention = new AttentionFragment();
                        transaction.add(R.id.main_frame_layout, attention);
                    } else {
                        transaction.show(attention);
                    }
                    break;
                case 3:
                    img_mine.setBackgroundResource(R.drawable.mine_select);
                    if (mine == null) {
                        mine = new MineFragment();
                        transaction.add(R.id.main_frame_layout, mine);
                    } else {
                        transaction.show(mine);
                    }
                    break;
            }
            transaction.commit();
        }
    

    4.隐藏

    	/**
         * 隐藏片段
         *
         * @param transaction
         */
        private void hideFragments(FragmentTransaction transaction) {
            if (home != null) {
                transaction.hide(home);
            }
            if (message != null) {
                transaction.hide(message);
            }
            if (attention != null) {
                transaction.hide(attention);
            }
            if (mine != null) {
                transaction.hide(mine);
            }
        }
    

    5.清除选中样式

    /**
         * 清除选中Fragment的样式
         */
        public void clearChoice() {
            img_home.setBackgroundResource(R.drawable.home_unselect);
            img_message.setBackgroundResource(R.drawable.message_unselect);
            img_attention.setBackgroundResource(R.drawable.attention_unselect);
            img_mine.setBackgroundResource(R.drawable.mine_unselect);
        }
    
    展开全文
  • 通过record_car和record_person的点击实现下边的fragment切换。 过程: 1.获取fragmentManager 2.获取FragmentTransaction 3.add/remove/hide/show等方法的使用,本例中使用的是add进去后,再通过使用show和...

     通过record_car和record_person的点击实现下边的fragment的切换。

    过程:

    1.获取fragmentManager

    2.获取FragmentTransaction

    3.add/remove/hide/show等方法的使用,本例中使用的是add进去后,再通过使用show和hide进行切换,没有使用remove。

     

    代码实例:

    public class RecordTabActivity extends FragmentActivity implements View.OnClickListener {
        private TextView record_person;
        private TextView record_car;
        private ImageView back;
        private View person_view;
        private View car_view;
        private RecordPersonFragment recordPersonFragment;
        private RecordCarFragment recordCarFragment;
        FragmentManager fragmentManager;
    
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_record_tab);
            initview();
        }
    
        private void initview() {
            record_person = (TextView)findViewById(R.id.record_person);
            record_car = (TextView)findViewById(R.id.record_car);
            back = (ImageView)findViewById(R.id.head_blue_back);
            person_view = (View)findViewById(R.id.person_view);
            car_view = (View)findViewById(R.id.car_view);
            record_person.setOnClickListener(this);
            record_car.setOnClickListener(this);
            back.setOnClickListener(this);
            fragmentManager = getFragmentManager();
            record_person.performClick();
        }
    
    
        @Override
        public void onClick(View v) {
            switch (v.getId()){
                case R.id.head_blue_back:
                    finish();
                    break;
                case R.id.record_person:
                    setTabSelection(0);
                    person_view.setVisibility(View.VISIBLE);
                    car_view.setVisibility(View.INVISIBLE);
                    break;
                case R.id.record_car:
                    setTabSelection(1);
                    person_view.setVisibility(View.INVISIBLE);
                    car_view.setVisibility(View.VISIBLE);
                    break;
                default:
                    break;
            }
        }
    
        private void setTabSelection(int index) {
            FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
            hideFragment(fragmentTransaction);
            switch (index){
                case 0:
                    if(recordPersonFragment == null){
                        recordPersonFragment = new RecordPersonFragment();
                        fragmentTransaction.add(R.id.record_fragment,recordPersonFragment);
                    }else {
                        fragmentTransaction.show(recordPersonFragment);
                    }
                    break;
                case 1:
                    if(recordCarFragment == null){
                        recordCarFragment = new RecordCarFragment();
                        fragmentTransaction.add(R.id.record_fragment,recordCarFragment);
                    }else {
                        fragmentTransaction.show(recordCarFragment);
                    }
                    break;
                default:
                    break;
            }
            fragmentTransaction.commit();
        }
    
        private void hideFragment(FragmentTransaction fragmentTransaction) {
            if(recordPersonFragment != null){
                fragmentTransaction.hide(recordPersonFragment);
            }
            if(recordCarFragment != null){
                fragmentTransaction.hide(recordCarFragment);
            }
        }
    }

     

    展开全文
  • 我想刚刚接触安卓的同学或许会这么写: FragmentManager fragmentManager=getSupportFragmentManager(); FragmentTransaction fragmentTransaction=fragmentManager.beginTransaction(); fragmentTransaction.add...
  • Android解决多个Fragment切换时布局重新实例化问题

    万次阅读 多人点赞 2018-06-14 10:40:37
    至于fragment的使用就不多说了,直奔主题, 布局文件:<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tool
  • 使用过app的人都知道,几乎所有的app都用到fragment进行首页分割,还有的加上了...对于fragment的使用就我所知就我会的只有两种吧,一种是add方式来进行show和add,这种方式你切换fragment不会让fragment重新刷新
  • 案例图片:XML&lt;LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="... andro...
  • fragment的两种切换方式: 1.通过add方法添加fragment,再通过hide,show决定显示哪一个fragment,此方式是将fragment隐藏而非重建 2.replace:每次都是重新创建fragment 用一个demo展示如下: 首页activity的...
  • 在项目中需要进行Fragment切换,一直都是用replace()方法来替换Fragment 但是,这样会有一个问题 ,应该很多朋友都遇到过: 每次切换的时候,Fragment都会重新实例化,也就是运行OnCreatVIew()方法 那么如何让多个...
  • Android fragment来回切换时,刷新数据

    万次阅读 2018-08-13 14:47:42
    一般,我们做项目,底部的4个fragment切换时,最好可以刷新数据 做fragment显影藏时,最好用hide,show 这时会有一个方法onHiddenChanged 在这里面我们可以刷新数据 还可以做这个操作——点当前tab,也刷新界面 ...
  • 至于fragment的用法,fragment+viewpager的滑动切换代码请参考博文 Android基础:翻页控件Viewpager的使用方法,viewpager+fragment混合使用 fragment与Activity 当在使用activity嵌套fragment,...
  • Fragment切换重新或不重新加载界面

    千次阅读 2016-06-06 15:28:29
    Fragment切换重新或不重新加载界面 在实现开发应用时,有时Fragment切换时界面的信息需要更新,则需要重新加载,否则不需要; 下面实现了默认的fragment 、 不重新加载 与 重新加载的方法,只需你自己的fragmeng和 ...
  • 转眼,已经凌晨四点半了,凌晨四点半的五道口很安静,很美。
  • Viewpager 中有两个pages,在每一个 fragment中,我放入一个按钮到switching fragment中,但是如果我改变方向,switching不能运行。对于switching fragment,我使用的是 OnChangePageButtonClick 接口。为什么会出现...
  • Fragment切换
  • fragment切换的时候其实是有系统的动画的 只是我们在使用过程中没有注意而已 使用FragmentTransaction transaction = mFragmentManager.beginTransaction();  获取到FragmentTransaction 对象,然后调用他的...
  • Android---fragment动态切换简单使用

    千次阅读 2019-04-26 13:33:01
    public class MainActivity extends AppCompatActivity implements View.OnClickListener { private FragmentManager manager; private FragmentTransaction transaction; private RadioButton rb_sh...
  •  我主要写的是一个fragment页面上的按钮点击切换到下一个fragment的页面,覆盖掉前一个fragment页面,不是主activity的按钮去控制切换不同的fragment。 说明:所用到的类FragmentManager和FragmentTransaction都是...
  • android fragment 刷新功能

    千次阅读 2017-08-21 10:54:07
    本文 介绍两点 已是fragment切换 一是fragment刷新 先说第一点 fragment切换 目前fragment在开发中应用越来越广泛 当然也非常方便 而我们切换fragment 也有两中方式 第一种是replace的方法进行的 这种方式...
1 2 3 4 5 ... 20
收藏数 37,057
精华内容 14,822
关键字:

fragment切换