1.概述
android开发者文档中是这么介绍fragment的:
Fragment
表示Activity
中的行为或用户界面部分。您可以将多个片段组合在一个 Activity 中来构建多窗格 UI,以及在多个 Activity 中重复使用某个片段。您可以将片段视为 Activity 的模块化组成部分,它具有自己的生命周期,能接收自己的输入事件,并且您可以在 Activity 运行时添加或移除片段(有点像您可以在不同 Activity 中重复使用的“子 Activity”)。fargment必须始终嵌入在 Activity 中,其生命周期直接受宿主 Activity 生命周期的影响。 例如,当 Activity 暂停时,其中的所有片段也会暂停;当 Activity 被销毁时,所有片段也会被销毁。 不过,当 Activity 正在运行(处于已恢复生命周期状态)时,您可以独立操纵每个片段,如添加或移除它们。
它的出现主要是为了给大屏幕(如平板电脑)上更加动态和灵活的 UI 设计提供支持。例如,新闻应用可以使用一个片段在左侧显示文章列表,使用另一个片段在右侧显示文章 — 两个片段并排显示在一个 Activity 中,每个片段都具有自己的一套生命周期回调方法,并各自处理自己的用户输入事件。 因此,用户不需要使用一个 Activity 来选择文章,然后使用另一个 Activity 来阅读文章,而是可以在同一个 Activity 内选择文章并进行阅读,如下图中的平板电脑布局所示。我们常用的微信、知乎等都是使用fragment。
2.fragment的生命周期
fragment的生命周期与activity的生命周期类似,它包含与 Activity 类似的回调方法,如 onCreate()
、onStart()
、onPause()
和 onStop()
。通常应该实现以下的几种方法:
onCreate()
:系统会在创建片段时调用此方法。您应该在实现内初始化您想在片段暂停或停止后恢复时保留的必需片段组件。
onCreateView()
:系统会在片段首次绘制其用户界面时调用此方法。 要想为您的片段绘制 UI,您从此方法中返回的 View
必须是片段布局的根视图。如果片段未提供 UI,您可以返回 null。
onPause()
:系统将此方法作为用户离开片段的第一个信号(但并不总是意味着此片段会被销毁)进行调用。 您通常应该在此方法内确认在当前用户会话结束后仍然有效的任何更改(因为用户可能不会返回)。
生命周期图如下:
从图中可以看出,如果我们的fragment一直存在不销毁的话,那么便一直不会返回onCreateView()。那么我们的fragment将是处于静态的,不会更新界面,除非存在某种监听,如按钮的监听。所以这种情况下,我们需要对fragment上的控件进行监听,当用户操作控件的时候,我们去更新界面。
3.在一个activity中添加fragment
3.1 添加布局文件
首先,需要在activity的layout中添加一个用来填充Fragemnt的ViewPage,如下所示:
<!-- activity_layout.xml -->
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
android:layout_width="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="match_parent"
android:orientation="vertical">
<android.support.v4.view.ViewPager
android:id="@+id/viewPager"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
>
</android.support.v4.view.ViewPager>
</LinearLayout>
再添加fragment的布局,这里我添加两个用于展示
第一个fragment,fragment1.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
android:layout_width="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="match_parent"
android:gravity="center"
android:orientation="vertical">
<TextView
android:text="Hello World!"
android:textSize="30dp"
android:layout_gravity="center"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
第二个fragment,fragment2.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
android:layout_width="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="match_parent"
android:gravity="center"
android:orientation="vertical">
<TextView
android:text="Hello World!"
android:textSize="30dp"
android:layout_gravity="center"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout>
3.2 添加java文件
对应以上两个fragment分别创建两个java文件:fragment1.java,fragment2.java
fragment1.java
package cn.edu.xidian.fragmenttest;
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;
/**
* Created by kabuto on 2018/1/17.
*/
public class fragment1 extends Fragment {
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, Bundle savedInstanceState) {
View view= inflater.inflate(R.layout.fragment1, container, false);
//对控件进行操作
return view;
}
}
fragment2.java
package cn.edu.xidian.fragmenttest;
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;
/**
* Created by kabuto on 2018/1/17.
*/
public class fragment2 extends Fragment {
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, Bundle savedInstanceState) {
View view= inflater.inflate(R.layout.fragment2, container, false);
//对控件进行操作
Button btn_config = view.findViewById(R.id.btn_confirm);
btn_config.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(getActivity(),"这是第二个fragment", Toast.LENGTH_LONG).show();
}
});
return view;
}
}
3.3 把fragment添加到activity中
Mainactivity.java
package cn.edu.xidian.fragmenttest;
import android.os.Bundle;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.view.ViewPager;
import android.support.v7.app.AppCompatActivity;
import java.util.ArrayList;
import java.util.List;
public class MainActivity extends AppCompatActivity {
private List<Fragment> mFragments;
private ViewPager mViewPager;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mViewPager = (ViewPager) findViewById(R.id.viewPager);
//添加fragmment
mFragments = new ArrayList<Fragment>();
mFragments.add(new fragment1());
mFragments.add(new fragment2());
//获取FragmentPagerAdapter
FragmentPagerAdapter adapter = new FragmentPagerAdapter(getSupportFragmentManager()) {
@Override
public int getCount() {
return mFragments.size();
}
@Override
public Fragment getItem(int position) {
return mFragments.get(position);
}
};
mViewPager.setAdapter(adapter);
mViewPager.setOffscreenPageLimit(adapter.getCount() - 1);//设置fragment显示数量
mViewPager.setCurrentItem(0); //设置初始显示页面
//监听mViewPager滑动事件
mViewPager.addOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener(){
@Override
public void onPageSelected(int position) {
mFragments.get(position).onAttach(MainActivity.this);
}
});
}
}
从Mainactivity中可以看出, 我们把两个fragment存放在一个list中; 使用FragmentPagerAdapter来放置这个list; 把这个adapter设置到viewpager中; 设置显示数量与显示界面; 最后监听滑动事件。 最后得到的效果如图所示: