继承自PagerAdapder的类
public class MyPagerAdapter extends PagerAdapter {
private List<View> mList;
private List<String> mTitleList;
public MyPagerAdapter(List<View> mList, List<String> mTitleList) {
this.mList = mList;
this.mTitleList = mTitleList;
}
@Override
public int getCount() {
return mList == null ? 0 : mList.size();
}
@Override
public boolean isViewFromObject(View view, Object object) {
return view==object;
}
@Override
public Object instantiateItem(ViewGroup container, int position) {
container.addView(mList.get(position));
return mList.get(position);
}
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
//调用父类的方法一定要删去 否则会报 Required method destroyItem was not overridden
// super.destroyItem(container, position, object);
container.removeView(mList.get(position));
}
@Override
public CharSequence getPageTitle(int position) {
return mTitleList.get(position);
}
}
我们的Activity
public class MainActivity extends AppCompatActivity {
private List<View> mList;
private List<String> mTitleList;
private ViewPager mVp;
private PagerTitleStrip mPts;
private MyPagerAdapter myPagerAdapter;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mVp = (ViewPager) findViewById(R.id.viewPager);
mPts = (PagerTitleStrip) findViewById(R.id.titleStrip);
mList = new ArrayList<>();
mList.add(new View(this));
mList.add(new View(this));
mList.add(new View(this));
mList.add(new View(this));
mTitleList = new ArrayList<>();
mTitleList.add("红");
mTitleList.add("黄");
mTitleList.add("蓝");
mTitleList.add("绿");
myPagerAdapter = new MyPagerAdapter(mList,mTitleList);
mVp.setAdapter(myPagerAdapter);
}
布局文件
<android.support.v4.view.ViewPager
android:id="@+id/viewPager"
android:layout_width="match_parent"
android:layout_height="match_parent">
<android.support.v4.view.PagerTitleStrip
android:id="@+id/titleStrip"
android:layout_width="wrap_content"
android:layout_height="wrap_content">
</android.support.v4.view.PagerTitleStrip>
</android.support.v4.view.ViewPager>
ViewPager的监听事件
viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
//positon:当前页面,就是你点击的页面
//positonOffset:当前页面偏移的百分比
//positionOffsetPostionPixels:当前页面偏移的像素位置
}
@Override
public void onPageSelected(int position) {
//方法当 页面完成跳转后会被调用
//所以这个position就是 跳转后的界面的位置
}
@Override
public void onPageScrollStateChanged(int state) {
//state的状态:0,1,2
//0.表示什么都没有做
//1.表示正在滑动
//2.表示滑动完毕
}
});
Fragement配合FragmentPagerAdaper的使用
1.需要注意的就是:使用FragmentPagerAdapter 时,Fragment对象会一直存留在内存中,所以当有大量的显示页时,就不适合用FragmentPagerAdapter 了,FragmentPagerAdapter 适用于只有少数的page情况,像选项卡。
2.当页面数比较多的时候可以考虑使用FragmentStatePagerAdapter ,当使用FragmentStatePagerAdapter 时,如果Fragment不显示,那么Fragment对象会被销毁,但在回调onDestroy()方法之前会回调onSaveInstanceState(Bundle outState)方法来保存Fragment的状态,下次Fragment显示时通过onCreate(Bundle savedInstanceState)把存储的状态值取出来,FragmentStatePagerAdapter 比较适合页面比较多的情况,像一个页面的ListView
总的来说 FragementPagerAdapter和FragmentStatePagerAdapter默认都是存在三个页面,但是FrgPagerAdaper的实例不会被销毁,只是不断的销毁重建视图,而FrgStatePagerAdaper会吧Frg的实例销毁掉
Fragment
public class MyFragment extends Fragment {
private int position;
public static MyFragment create(int position){
MyFragment fragment = new MyFragment();
Bundle bundle = new Bundle();
bundle.putInt("position",position);
fragment.setArguments(bundle);
return fragment;
}
@Override
public void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
position = getArguments().getInt("position");
Log.i("Frg","onCreate"+position);
}
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.frg,null);
ImageView img = (ImageView) view.findViewById(R.id.img);
switch (position) {
case 0:
img.setBackgroundResource(R.color.colorAccent);
break;
case 1:
img.setBackgroundResource(R.color.colorPrimary);
break;
case 2:
img.setBackgroundResource(R.color.colorPrimaryDark);
break;
}
return view;
}
@Override
public void onViewCreated(View view, @Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
Log.i("Frg","onViewCreated"+position);
}
@Override
public void onDestroyView() {
super.onDestroyView();
Log.i("Frg","onDestroyView"+position);
}
@Override
public void onDestroy() {
super.onDestroy();
Log.i("Frg","onDestroy"+position);
}
}
在Fragment中打印了生命周期 可以看什么时候销毁实例 什么时候是销毁视图
FragmentPagerAdapter
public class MyFrgPagerAdapter extends FragmentPagerAdapter {
private List<Fragment> mList;
private List<String> mTitileList;
public MyFrgPagerAdapter(FragmentManager fm,List<Fragment> mList,List<String> mTitileList) {
super(fm);
this.mList = mList;
this.mTitileList = mTitileList;
}
@Override
public Fragment getItem(int position) {
return mList.get(position);
}
@Override
public int getCount() {
return mList.size();
}
@Override
public CharSequence getPageTitle(int position) {
return mTitileList.get(position);
}
}
FragmentStateAdapter
public class MyfragmentStateAdapter extends FragmentStatePagerAdapter {
private List<Fragment> mList;
public MyfragmentStateAdapter(FragmentManager fm,List<Fragment> mList) {
super(fm);
this.mList = mList;
}
@Override
public Fragment getItem(int position) {
return mList.get(position);
}
@Override
public int getCount() {
return mList.size();
}
}
Activity
public class MainActivity extends AppCompatActivity {
private List<View> mList;
private List<String> mTitleList;
private ViewPager mVp;
private PagerTitleStrip mPts;
private MyPagerAdapter myPagerAdapter;
private PagerTabStrip mTab;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mVp = (ViewPager) findViewById(R.id.viewPager);
// mPts = (PagerTitleStrip) findViewById(R.id.titleStrip);//我们可以在这里对指示器进行设置 颜色啊什么的
mTab = (PagerTabStrip) findViewById(R.id.tab);
mTitleList = new ArrayList<>();
mTitleList.add("红");
mTitleList.add("黄");
mTitleList.add("蓝");
mTitleList.add("绿");
List<Fragment> mList = new ArrayList<>();
mList.add(MyFragment.create(0));
mList.add(MyFragment.create(1));
mList.add(MyFragment.create(2));
mList.add(MyFragment.create(3));
mVp.setAdapter(new MyFrgPagerAdapter(getSupportFragmentManager(),mList,mTitleList));//在这个Adapter中测试了两种Tab的不同效果 具体不同之处看布局
// mVp.setAdapter(new MyfragmentStateAdapter(getSupportFragmentManager(),mList));
}
}
布局文件
<android.support.v4.view.ViewPager
android:id="@+id/viewPager"
android:layout_width="match_parent"
android:layout_height="match_parent">
<!--<android.support.v4.view.PagerTitleStrip-->
<!--android:id="@+id/titleStrip"-->
<!--android:layout_width="wrap_content"-->
<!--android:layout_height="wrap_content">-->
<!--</android.support.v4.view.PagerTitleStrip>-->
<android.support.v4.view.PagerTabStrip
android:id="@+id/tab"
android:layout_width="wrap_content"
android:layout_height="wrap_content"></android.support.v4.view.PagerTabStrip>
</android.support.v4.view.ViewPager>
当然了 系统提供给我们的指示器是远远不够用的而且效果达不到我们期望的效果。那么就让我们使用TabLayout吧
TabLayout
首先我们需要design包的导入
compile 'com.android.support:design:25.0.0'
TabLayout的话我们可以定制,我们先看布局文件
//我们引入的是材料包里面的TabLayout
<android.support.design.widget.TabLayout
android:id="@+id/tabLayout"
style="@style/MyTabStyle"
android:layout_width="match_parent"
android:layout_height="wrap_content"></android.support.design.widget.TabLayout>
<android.support.v4.view.ViewPager
android:id="@+id/viewPager"
android:layout_width="match_parent"
android:layout_height="match_parent">
</android.support.v4.view.ViewPager>
tabLayout的app:tabMode=”scrollable”属性可以根据tab数量的多少设置fixed还是scrollable
样式
具体的样子可以根据自的需要调整
<style name="MyTabStyle" parent="Widget.Design.TabLayout">
<item name="tabMaxWidth">36dp</item> <!--TAB最大宽度-->
<item name="tabIndicatorColor">?attr/colorAccent</item> <!--TAB底部滑块颜色-->
<item name="tabIndicatorHeight">5dp</item> <!--TAB底部滑块高度-->
<item name="tabPaddingStart">12dp</item> <!--TAB左边padding-->
<item name="tabPaddingEnd">12dp</item> <!--TAB右边padding-->
<item name="tabBackground">?attr/selectableItemBackground</item> <!--TAB背景色-->
<item name="tabTextAppearance">@style/MyTabTextStyle</item> <!--TAB文字样式-->
<item name="tabSelectedTextColor">?android:textColorPrimary</item> <!--TAB选中文字颜色-->
</style>
<style name="MyTabTextStyle" parent="TextAppearance.Design.Tab"> <!--TAB文字样式-->
<item name="android:textSize">14sp</item><!--文字大小-->
<item name="android:textColor">?android:textColorSecondary</item><!--文字颜色-->
<item name="textAllCaps">false</item> <!--英文大写,默认true-->
</style>
最后的Activity
其实就一行关键代码:tabLayout.setupWithViewPager(mVp);
public class MainActivity extends AppCompatActivity {
private List<View> mList;
private List<String> mTitleList;
private ViewPager mVp;
private PagerTitleStrip mPts;
private MyPagerAdapter myPagerAdapter;
private PagerTabStrip mTab;
private TabLayout tabLayout;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mVp = (ViewPager) findViewById(R.id.viewPager);
// mPts = (PagerTitleStrip) findViewById(R.id.titleStrip);
// mTab = (PagerTabStrip) findViewById(R.id.tab);
tabLayout = (TabLayout) findViewById(R.id.tabLayout);
mList = new ArrayList<>();
mList.add(new View(this));
mList.add(new View(this));
mList.add(new View(this));
mList.add(new View(this));
mTitleList = new ArrayList<>();
mTitleList.add("红");
mTitleList.add("黄");
mTitleList.add("蓝");
mTitleList.add("绿");
myPagerAdapter = new MyPagerAdapter(mList,mTitleList);
// mVp.setAdapter(myPagerAdapter);
List<Fragment> mList = new ArrayList<>();
mList.add(MyFragment.create(0));
mList.add(MyFragment.create(1));
mList.add(MyFragment.create(2));
mList.add(MyFragment.create(3));
mVp.setAdapter(new MyFrgPagerAdapter(getSupportFragmentManager(),mList,mTitleList));
tabLayout.setupWithViewPager(mVp);
// mVp.setAdapter(new MyfragmentStateAdapter(getSupportFragmentManager(),mList));
}
}
这样子实现的效果只是文字来指示的效果,但是我们通常要的效果是图片加文字的效果呢,这就需要我们自定义Tab的View了
自定义Tab的View效果
Adapter
public class MyFrgPagerAdapter extends FragmentPagerAdapter {
private List<Fragment> mList;
private List<String> mTitileList;
private Context mContext;
public MyFrgPagerAdapter(FragmentManager fm,List<Fragment> mList,List<String> mTitileList,Context context) {
super(fm);
this.mList = mList;
this.mTitileList = mTitileList;
this.mContext = context;
}
@Override
public Fragment getItem(int position) {
return mList.get(position);
}
@Override
public int getCount() {
return mList.size();
}
@Override
public CharSequence getPageTitle(int position) {
return null;//因为要使用自定义的Tab的View这里的就不需要了
}
public View getTabView(int position){
View view = LayoutInflater.from(mContext).inflate(R.layout.tab_layout,null);
ImageView img = (ImageView) view.findViewById(R.id.img);
img.setImageResource(R.mipmap.ic_launcher);
return view;
}
}
这里的getView我们没有硬性的写在哪里 可以写在activity中也可以写在其他地方 只要是根据每一个页面和tab来设置View即可
这里的布局只是实现了一个简单的小机器人的指示器
Activity
public class MainActivity extends AppCompatActivity {
private ViewPager mVp;
private MyFrgPagerAdapter myFrgPagerAdapter;
private TabLayout tabLayout;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mVp = (ViewPager) findViewById(R.id.viewPager);
tabLayout = (TabLayout) findViewById(R.id.tabLayout);
List<Fragment> mList = new ArrayList<>();
mList.add(MyFragment.create(0));
mList.add(MyFragment.create(1));
mList.add(MyFragment.create(2));
mList.add(MyFragment.create(3));
myFrgPagerAdapter = new MyFrgPagerAdapter(getSupportFragmentManager(),mList,mTitleList,this);
mVp.setAdapter(myFrgPagerAdapter);
tabLayout.setupWithViewPager(mVp);
for(int i = 0;i<tabLayout.getTabCount();i++){
TabLayout.Tab tab = tabLayout.getTabAt(i);
tab.setCustomView(myFrgPagerAdapter.getTabView(i));
}
}
}