一、概述

在2015年的google大会上,google发布了新的Android Support Design库,里面包含了几个新的控件,其中就有一个TabLayout,它就可以完成TabPageIndicator的效果,而且还是官方的,最好的是它可以兼容到2.2以上版本,包括2.2。
依稀记得前几年要实现这样的功能用的还是viewpagerindicator开源库,如今既然谷歌推出了TabLayout,所以特地学习了一下。
使用之前需要添加依赖:

compile 'com.android.support:design:24.2.1'

二、实现效果图

Android标签页TabLayout控件实战及ViewPager取消预加载_android

TabLayout一般都是配合着ViewPager使用,众所周知,ViewPager有个预加载功能,在加载本页数据时,它会提前加载下页数据,可以极大的浪费资源,而且不利于用户体验,你如果调试我的源码就会发现,本文特地取消了ViewPager预加载。
主要是初始化Frament时给每个Fragment设置一个mTabPos常量,第一次进入时加以判断setCurrentItem的页是否和mTabPos相同,如果相同就加载,这样第一次就不会预加载,后面进行页面切换时,通过onPageSelected方法加载。

三、核心代码

1.页面TabLayoutTestActivity.java

package com.czhappy.effectdemo.activity;

import android.os.Bundle;
import android.support.annotation.Nullable;
import android.support.design.widget.TabLayout;
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v4.app.FragmentPagerAdapter;
import android.support.v4.view.ViewPager;
import android.support.v7.app.AppCompatActivity;

import com.czhappy.effectdemo.R;
import com.czhappy.effectdemo.fragment.PageFragment;

import java.util.ArrayList;
import java.util.List;

/**
* Description:
* User: chenzheng
* Date: 2017/1/20 0020
* Time: 14:24
*/
public class TabLayoutTestActivity extends AppCompatActivity {

private TabLayout mTabLayout;
private ViewPager mViewPager;

private SimpleFragmentPagerAdapter mAdapter;
private List<Fragment> mFragments = new ArrayList<Fragment>();
private String tabTitles[] = new String[]{"tab1","tab2","tab3", "tab4","tab5","tab6"};

private int curTab=0;

@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
this.setContentView(R.layout.activity_tablayout_test);

initView();
}

private void initView() {
mTabLayout = (TabLayout) this.findViewById(R.id.layout_tab);
mViewPager = (ViewPager) this.findViewById(R.id.view_pager);

for(int i=0; i<tabTitles.length; i++){
PageFragment fragment = new PageFragment(curTab);
fragment.setTabPos(i);
mFragments.add(fragment);
}
mAdapter = new SimpleFragmentPagerAdapter(getSupportFragmentManager(), mFragments);
mViewPager.setAdapter(mAdapter);
mTabLayout.setupWithViewPager(mViewPager);
mTabLayout.setSmoothScrollingEnabled(true);
//mTabLayout.setTabMode(TabLayout.MODE_FIXED);//全部放下,不滑动
mTabLayout.setTabMode(TabLayout.MODE_SCROLLABLE);//超过长度可滑动
//设置当前显示哪个标签页
mViewPager.setCurrentItem(curTab);
mViewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {

}

@Override
public void onPageSelected(int position) {
//滑动监听加载数据,一次只加载一个标签页
((PageFragment)mAdapter.getItem(position)).sendMessage();
}

@Override
public void onPageScrollStateChanged(int state) {

}
});
}

class SimpleFragmentPagerAdapter extends FragmentPagerAdapter {

private List<Fragment> fragments;

public SimpleFragmentPagerAdapter(FragmentManager fm, List<Fragment> fragments) {
super(fm);
this.fragments = fragments;
}

@Override
public Fragment getItem(int position) {
return fragments.get(position);
}

@Override
public int getCount() {
return tabTitles.length;
}

@Override
public CharSequence getPageTitle(int position) {
return tabTitles[position];
}

//防止fragment自动销毁
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
//super.destroyItem(container, position, object);
}
}
}

2.布局activity_tablayout_test.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"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">

<android.support.design.widget.TabLayout
android:id="@+id/layout_tab"
android:layout_width="match_parent"
android:layout_height="32dp"
app:tabIndicatorColor="@color/actionbar_background"
app:tabMode="scrollable"
app:tabSelectedTextColor="?attr/colorPrimary"
app:tabTextColor="@color/project_listitem_someinfo" />


<android.support.v4.view.ViewPager
android:id="@+id/view_pager"
android:layout_width="match_parent"
android:layout_height="match_parent" />

</LinearLayout>

3.PageFragment.java

package com.czhappy.effectdemo.fragment;

import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
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;
import android.widget.TextView;

import com.czhappy.effectdemo.R;

/**
* Description:
* User: chenzheng
* Date: 2017/1/20 0020
* Time: 15:18
*/
public class PageFragment extends Fragment {

public static final String ARG_PAGE = "ARG_PAGE";
private boolean IS_LOADED = false;
private static int mSerial=0;
private int mTabPos=0;
private boolean isFirst = true;

private Handler handler = new Handler(){
public void handleMessage(android.os.Message msg) {
Log.e("tag", "IS_LOADED="+IS_LOADED);
if(!IS_LOADED){
IS_LOADED = true;
//这里执行加载数据的操作
Log.e("tag", "我是page"+(mTabPos+1));
}
return;
};
};

public PageFragment(int serial){
mSerial = serial;
}

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.e("tag","onCreate()方法执行");

}

public void sendMessage(){
Message message = handler.obtainMessage();
message.sendToTarget();
}

public void setTabPos(int mTabPos) {
this.mTabPos = mTabPos;
}

@Nullable
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
Log.e("tag","onCreateView()方法执行");
View view = inflater.inflate(R.layout.fragment_page, container, false);
TextView textView = (TextView) view.findViewById(R.id.content);
textView.setText("我是page" + (mTabPos+1));
//设置页和当前页一致时加载,防止预加载
if (isFirst && mTabPos==mSerial) {
isFirst = false;
sendMessage();
}
return view;
}

@Override
public void onDestroyView() {
super.onDestroyView();
Log.e("tag","onDestroyView()方法执行");
}
}

4.Fragment布局文件fragment_page.xml

<?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:background="#fff"
android:gravity="center"
android:orientation="vertical">

<TextView
android:id="@+id/content"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="16sp"
android:text="我是page1"/>

</LinearLayout>