1、fragment的简单介绍。
首先fragment的优点:
fragment可以为不同屏幕大小的设备创建动态灵活的UI(小屏幕手机到大屏幕平板电脑),极大提高了UI的灵活性。
每个frgment都是独立的,可以被多个activity公用,可以在一个正在显示的activity中执行添加、替换、删除的操作。
2、fragment的生命周期
package com.example.apple.myfilemanager;
import android.app.Activity;
import android.content.Context;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
/**
* Created by apple on 17/5/4.
*/
public class Fragment1 extends Fragment {
private final String TAG = "Fragment1";
/**
* 一旦fragment已被创建,要创建它自己的用户界面时调用
* @param inflater
* @param container
* @param savedInstanceState
* @return
*/
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_1,null);
Log.e(TAG,"每次创建都会去绘制Fragment的View组件时回调该方法;");
return view;
}
/**
* 调用该方法时fragment会被连接到它的父activity上
* @param activity
*/
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);//获取对父Activity的引用
Log.e(TAG,"当Fragment被添加到Activity时候会回调这个方法,并且只调用一次;");
}
@Override
public void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.d(TAG,"创建Fragment时会回调,只会调用一次;");
}
@Override
public void onActivityCreated(@Nullable Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
Log.e(TAG,"当Fragment所在的Activity启动完成后调用,即父activity和fragment Ui已经被创建;");
}
@Override
public void onStart() {
super.onStart();
Log.e(TAG,"启动Fragment,即fragment现在可见时");
}
@Override
public void onResume() {
super.onResume();
Log.e(TAG,"恢复Fragment时会被回调(ui、线程或进程),调用onStart()方法后面一定会调用onResume()方法;");
}
@Override
public void onPause() {
super.onPause();
Log.e(TAG,"当activity不是活动的前台时,需要暂停ui的更新、挂起线程或者暂停那些不需要更新的cpu的集中处理。由于调用该方法后,进程可能被终止" +
"所以要保存所有的编辑和状态改变信息");
}
@Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
Log.e(TAG,"在活动生命周期结束时,调用该方法保存ui");
}
/**
* 可见生命周期结束时调用
*/
@Override
public void onStop() {
super.onStop();
Log.e(TAG,"停止Fragment");
}
/**
* fragment的view被分离时调用
*/
@Override
public void onDestroyView() {
super.onDestroyView();
Log.e(TAG,"清除资源相关的view");
}
@Override
public void onDestroy() {
super.onDestroy();
Log.e(TAG,"销毁Fragment所包含的View组件时调用");
}
@Override
public void onDetach() {
super.onDetach();
Log.e(TAG,"Fragment从Activity中删除时会回调该方法,并且这个方法只会调用一次");
}
}
3、fragment Manager
每个activity都包含一个fragment manger来管理fragment
fragmentManager = getSupportFragmentManager();
fragment Manager提供了很多方法用来访问添加到activity上的fragment,通过执行fragment transaction来添加、删除和替换。 beginTransaction.add(R.id.framelayout, fragment, tag);
//beginTransaction.replace(R.id.framelayout,fragment);
// beginTransaction.remove(fragment);
4、在activity中添加fragment
首先布局中代码
<FrameLayout
android:id="@+id/framelayout"
android:layout_width="match_parent"
android:layout_height="match_parent">
</FrameLayout>
在代码中实现添加、删除、替换fragment操作,但是首先要先添加fragment时要先指定一个tag标识,后面就可以通过这个标识通过findFrgmentByTag方法找到相应的fragment.
private void addFragment(Fragment fragment,String tag){
//获取事务
FragmentTransaction beginTransaction = fragmentManager.beginTransaction();
//第一个参数:要添加fragment容器
beginTransaction.add(R.id.framelayout, fragment, tag);
//beginTransaction.replace(R.id.framelayout,fragment);
// beginTransaction.remove(fragment);
//将当前fragment添加到回退栈
beginTransaction.addToBackStack(tag);
//提交
beginTransaction.commit();
}
删除fragnment通过查找到对应id然后删除
FragmentTransaction beginTransaction = fragmentManager.beginTransaction();
Fragment fragment1 = fragmentManager.findFragmentById(R.id.fragment1);
beginTransaction.remove(fragment1);
替换另一个fragment实现,可以使用replace,指定替换的fragment父容器的id。
private void replaceFragment(Fragment fragment){
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
fragmentTransaction.replace(R.id.framelayout,fragment);
fragmentTransaction.commit();
}
5、回退栈
fragment可以创建动态的activity布局,可以使ui界面改变,某些情况下可以视为一个新的屏幕,然后我们就可以使用回退栈了,可以回滚到之前的屏幕状态。
首先回滚到上一屏幕实现
ragmentManager.popBackStack("fragment2",0);
还可以定tag标识回滚到特定的一屏
fragmentManager.popBackStack("fragment2",FragmentManager.POP_BACK_STACK_INCLUSIVE);
通过点击进去还可以看到很多回滚的方法,可根据实际需求使用
public abstract void popBackStack();
public abstract boolean popBackStackImmediate();
public abstract boolean popBackStackImmediate(String name, int flags);
除了上面的还可以实现统计回退栈中有多少个fragment,然后就可以通过判断标识tag回退到特定界面
int backStackEntryCount = fragmentManager.getBackStackEntryCount();
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
//回退栈中一共有多少个fragment
int backStackEntryCount = fragmentManager.getBackStackEntryCount();
if (backStackEntryCount > 1) {
fragmentManager.popBackStackImmediate();
//获取当前回退到什么位置---获取某个索引值下的栈内容
FragmentManager.BackStackEntry backStackEntry = fragmentManager
.getBackStackEntryAt(fragmentManager
.getBackStackEntryCount() - 1);
String tagName = backStackEntry.getName();
if ("fragment1".equals(tagName)) {
rg.check(R.id.rb_first);
} else if ("fragment2".equals(tagName)) {
rg.check(R.id.rb_second);
} else if ("fragment3".equals(tagName)) {
rg.check(R.id.rb_three);
} else if ("fragment4".equals(tagName)) {
rg.check(R.id.rb_four);
}
} else {
finish();
}
}
//处理按键事件
return true;
}
如果我们要回退到最后一个,也可以像下面这样做,先统计回退栈中有多少个fragment然后通过判断一直回退到最后一个。
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
//回退栈中一共有多少个fragment
int backStackEntryCount = fragmentManager.getBackStackEntryCount();
if (backStackEntryCount > 1) {
//如果栈里面大于1,一直回退到最后一个
while (fragmentManager.getBackStackEntryCount()>1){
fragmentManager.popBackStackImmediate();
rg.check(R.id.rb_first);
}
} else {
finish();
}
}
//处理按键事件
return true;
}
6、实现fragment和activity 之间接口
package com.example.apple.myfilemanager;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
/**
* Created by apple on 17/5/4.
*/
public class Fragment2 extends Fragment implements View.OnClickListener{
private final String TAG = "Fragment2";
private Button btnFragment2;
private Fragment2BtnClickListener fragment2BtnClickListener ;
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_2, container, false);
btnFragment2 = (Button)view.findViewById(R.id.btn_fragment2);
btnFragment2.setOnClickListener(this);
return view;
}
@Override
public void onClick(View v) {
if(fragment2BtnClickListener != null) {
fragment2BtnClickListener.onFTwoBtnClick(v);
}
}
public interface Fragment2BtnClickListener {
void onFTwoBtnClick(View v);
}
//设置回调接口
public void setFragment2BtnClickListener(Fragment2BtnClickListener fragment2BtnClickListenr) {
this.fragment2BtnClickListener = fragment2BtnClickListenr;
}
}
activity中使用
fragment2 = new Fragment2();
fragment2.setFragment2BtnClickListener(new Fragment2.Fragment2BtnClickListener() {
@Override
public void onFTwoBtnClick(View v) {
}
});
7、实现activity之间传值
private void sendData(){
FragmentTransaction beginTransaction = fragmentManager.beginTransaction();
Fragment1 fragment1 = new Fragment1();
Bundle bundle = new Bundle();
bundle.putString("str","fragment1");
fragment1.setArguments(bundle);
beginTransaction.replace(R.id.framelayout, fragment1);
beginTransaction.commit();
}
fragment中获取activity传递过来的值
package com.example.apple.myfilemanager;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
/**
* Created by apple on
*/
public class Fragment3 extends Fragment {
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_3,null);
Bundle bundle = getArguments();//从activity传过来的Bundle
if(bundle!=null){
Log.e("fragment3",bundle.getString("str"));
}
return view;
}
}
最后fragment就学到这里。