安徽党组织标准化建设网站国内十大4a广告公司
03 Android基础--fragment
- 什么是fragment?
- fragment生命周期?
- 动态的fragment与静态的fragment
- fragment常用的两个类与API
- Fragment与Activity通信
什么是fragment?
碎片
,一个activity中可以使用多个fragment,可以把activity看成碎片
的容器。fragment也有自己的生命周期
fragment生命周期?
需要知道的是:
创建和重建
过程: Activity生命周期优先于Fragment
暂停和销毁
过程: Fragment生命周期优先于Activity
动态的fragment与静态的fragment
一个xml写,一个用Java代码写。
// 静态的fragment// 第一步:编写fragment所需要的XML文件
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools"android:layout_width="match_parent"android:layout_height="match_parent"tools:context=".BlankFragment1"><TextViewandroid:id="@+id/textView"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="TextView"android:textSize="30dp"/><Buttonandroid:id="@+id/button"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginTop="100dp"android:text="Button" />
</FrameLayout>// 第二步:编写activity所需要的XML文件,把fragment的XML定位到activity所需的XML文件中。
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:app="http://schemas.android.com/apk/res-auto"xmlns:tools="http://schemas.android.com/tools"android:layout_width="match_parent"android:layout_height="match_parent"android:orientation="vertical"tools:context=".MainActivity"><!-- name为确定 这个fragment绑定的哪个,id必须设置,因为资源管理会使用。一个avtivity可以包含多个fragment--><fragmentandroid:id="@+id/fragment1"android:name="com.example.fifthdemo_framgent_01.BlankFragment1"android:layout_width="match_parent"android:layout_height="match_parent"android:layout_weight="1"/></LinearLayout>// 第三步:编写fragment本身的代码
public class BlankFragment1 extends Fragment {private View root;private TextView textView;private Button button;@Overridepublic void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);}@Overridepublic View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {if (root == null) {root = inflater.inflate(R.layout.fragment_blank1, container, false);}textView = root.findViewById(R.id.textView);button = root.findViewById(R.id.button);button.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View view) {textView.setText("button setOnClickListener");}});return root;}
}// 第四步:编写activity。这个时候,fragment就会被渲染到activity中了。
public class MainActivity extends AppCompatActivity implements View.OnClickListener {@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);}
}
// 动态的fragment:一般都用这个// 第一步:编写fragment所需要的XML文件
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:tools="http://schemas.android.com/tools"android:layout_width="match_parent"android:layout_height="match_parent"tools:context=".BlankFragment1"><TextViewandroid:id="@+id/textView"android:layout_width="wrap_content"android:layout_height="wrap_content"android:text="TextView"android:textSize="30dp"/><Buttonandroid:id="@+id/button"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_marginTop="100dp"android:text="Button" />
</FrameLayout>// 第二步:编写fragment本身的代码
public class BlankFragment1 extends Fragment {private View root;private TextView textView;private Button button;@Overridepublic void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);}@Overridepublic View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {if (root == null) {root = inflater.inflate(R.layout.fragment_blank1, container, false);}textView = root.findViewById(R.id.textView);button = root.findViewById(R.id.button);button.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View view) {textView.setText("button setOnClickListener");}});return root;}
}// 第三步:编写activity所需要的XML文件
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"xmlns:app="http://schemas.android.com/apk/res-auto"xmlns:tools="http://schemas.android.com/tools"android:layout_width="match_parent"android:layout_height="match_parent"android:orientation="vertical"tools:context=".MainActivity"><Buttonandroid:id="@+id/bt1"android:layout_width="match_parent"android:layout_height="wrap_content"android:text="add fragment" /><Buttonandroid:id="@+id/bt2"android:layout_width="match_parent"android:layout_height="wrap_content"android:text="repalce" /><!-- fragment的容器,将来动态创建的fragment直接放这里面--><FrameLayoutandroid:id="@+id/framelayout_1"android:layout_width="match_parent"android:layout_height="match_parent"android:background="#A68EA3"/></LinearLayout>// 第四步:编写activity,动态的创建fragment
public class MainActivity extends AppCompatActivity implements View.OnClickListener {@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);Button button1 = findViewById(R.id.bt1);button1.setOnClickListener(this);Button button2 = findViewById(R.id.bt2);button2.setOnClickListener(this);}@Overridepublic void onClick(View view) { //点击事件switch (view.getId()) {case R.id.bt1: replaceFragment(new BlankFragment1());break;case R.id.bt2: replaceFragment(new ItemFragment2());break;}}private void replaceFragment(Fragment fragment) {//获取Fragment的管理器类 FragmentManagerFragmentManager fragmentManager = getSupportFragmentManager();//获取 FragmentManager中用于 Fragment 替换之类的类 FragmentTransactionFragmentTransaction transaction = fragmentManager.beginTransaction();//创建一个替换Fragment的事件transaction.replace(R.id.framelayout_1,fragment); // 替换的是framelayout_1中的fragment//将新的Fragment对象压入一个栈内,点击back会进行回退,而非退出apptransaction.addToBackStack(null);//提交事件transaction.commit();}
}
补充:FragmentManager支持链式调用:
// FragmentManager支持链式调用:
FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction().replace(R.id.fragment_container, ExampleFragment.class, null).setReorderingAllowed(true).addToBackStack("name") // name can be null.commit();
fragment常用的两个类与API
常用的类
- FragmentManager :顾名思义是负责管理Fragment的管理类,可以对Fragment进行添加、移除、替换等操作。在activity中操作。
- FragmentTransaction :通过FragmentManager获得,保证了fragment操作的原子性。
常用的API
- FragmentTransaction transaction = fm.benginTransatcion();//开启一个事务
- transaction.add();//让Activity中添加一个Fragment
- transaction.remove();//从Activity移除一个Fragment,如果被移除的
Fragment没有添加到回退栈,这个Fragment事例将会被销毁。 - transaction.replace();//使用另一个Fragment替换当前到,就相当于remove()以后,再add()
- transaction.hide();//隐藏当前的Fragment。
- Transaction.show();//显示之前隐藏的Fragment
- detach();//将view从UI中移除和remove()不同,此时Fragment的状态依然由FragmentManager维护。
- attach();重建view视图,附加到UI上并显示。
- transaction.commit();//提交一个事务。
Fragment与Activity通信
有很多种,接下来说一些常用的
- 通过构造器
- 通过ViewModel
- 通过EventBus
- 通过接口回调
- 通过Handler
- 通过广播
接下来介绍两种最常用的:
// 通过构造器,在activity中。FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();Fragment fragTop = new FrameTop();fragmentTransaction.replace(R.id.frame1,fragTop);Bundle bundle = new Bundle();fragTop.setArguments(bundle);bundle.putString("name","fragTop");fragmentTransaction.commit();// 在fragment中获取@Overridepublic void onAttach(@NonNull Context context) {super.onAttach(context);Bundle arguments = getArguments();String name = arguments.getString("name");}
// 通过viewModel,将来这个最常用
// 官方文档代码示例:
public class SharedViewModel extends ViewModel {private final MutableLiveData<Item> selected = new MutableLiveData<Item>();public void select(Item item) {selected.setValue(item);}public LiveData<Item> getSelected() {return selected;}
}public class ListFragment extends Fragment {private SharedViewModel model;public void onViewCreated(@NonNull View view, Bundle savedInstanceState) {super.onViewCreated(view, savedInstanceState);model = new ViewModelProvider(requireActivity()).get(SharedViewModel.class);itemSelector.setOnClickListener(item -> {model.select(item);});}
}public class DetailFragment extends Fragment {public void onViewCreated(@NonNull View view, Bundle savedInstanceState) {super.onViewCreated(view, savedInstanceState);SharedViewModel model = new ViewModelProvider(requireActivity()).get(SharedViewModel.class);model.getSelected().observe(getViewLifecycleOwner(), item -> {// Update the UI.});}
}