Android自带的TabLayout在support包中,导包:
implementation 'com.android.support:support-v4:27.1.1'
复制代码
效果1
不带viewpager,tab只可点击,就是普通的控件。
TabLayout嵌套TabItem,可改造空间有限。tabLayout只能嵌套TabItem,其余会报错。
"@+id/tabLayout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#e1e1e1"
app:tabSelectedTextColor="@color/colorAccent"
app:tabTextColor="@color/black"
app:tabIndicatorColor="@color/colorAccent"
app:tabMode="fixed"
app:tabIndicatorHeight="4dp">
"@+id/tab1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/tab1"/>
"@+id/tab2"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/tab2"/>
"@+id/tab3"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/tab3"/>
复制代码
效果2
fragment + viewpager + tabLayout
虽然看着没多大区别,但里面是嵌套了3个Fragment,可以左右切换。
tabLayout.setupWithViewPager(viewPager) 执行这句之后,tabLayout布局嵌套的tabItem会失效,展示的每个tab是通过FragmentPagerAdapter的getPageTitle来获取的。等会儿可以源码解释下。
xml布局:就是简单的tabLayout和viewPager嵌套在一个垂直的linearLayout中
"1.0" encoding="utf-8"?>
"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=".tablayout.TabLayoutActivity">
"@+id/tabLayout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#e1e1e1"
app:tabSelectedTextColor="@color/colorAccent"
app:tabTextColor="@color/black"
app:tabIndicatorColor="@color/colorAccent"
app:tabMode="fixed"
app:tabIndicatorHeight="4dp"/>
"@+id/viewPager"
android:layout_width="match_parent"
android:layout_height="match_parent"/>
复制代码
kotlin代码
class TabLayoutActivity : AppCompatActivity() {
var mFragmentList = arrayListOf()
val mTabTitle = listOf("英语", "数学", "语文")
var mAdapter: FragmentPagerAdapter? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_tab_layout)
initTabLayout()
}
private fun initTabLayout() {
mFragmentList.add(FragmentOne())
mFragmentList.add(FragmentTwo())
mFragmentList.add(FragmentThree())
mAdapter = FragmentPagerAdapterNew(supportFragmentManager, mFragmentList, mTabTitle)
viewPager.adapter = mAdapter //设置viewPager的adapter
tabLayout.setupWithViewPager(viewPager) //建立tabLayout和ViewPager的联系
}
class FragmentPagerAdapterNew(val fragementManager: FragmentManager,
val mFragmentList: List,
val mTabTitle: List)
: FragmentPagerAdapter(fragementManager) {
override fun getItem(position: Int): Fragment {
return mFragmentList[position] //切换tab展示的fragment
}
override fun getCount(): Int {
return mFragmentList.size //总共有多少个tab/fragment
}
override fun getPageTitle(position: Int): CharSequence? {
return mTabTitle[position] //展示tab的标题
}
}
}
复制代码
效果3
tab展示文字+图片的效果自行百度吧,因为我不打算用这个控件在项目中,用一个开源的更简单的FlycoTabLayout,下一篇就讲这个开源控件。
setViewPagerAdapter(viewPager)
现在解释下setViewPagerAdapter(viewPager)之后,tabLayout中的tabItem失效
首先removeAllTabs,然后根据mPagerAdapter.getCount得到tab个数,然后一个个通过addTab添加进行,newTab().setText(mPagerAdapter.getPageTitle(i)) tab设置的text就是我们刚刚说的, FragmentPagerAdapter里getPagerTitle()返回的啦
省略大部分代码
public void setupWithViewPager(@Nullable ViewPager viewPager) {
setupWithViewPager(viewPager, true);
}
public void setupWithViewPager(@Nullable final ViewPager viewPager, boolean autoRefresh) {
setupWithViewPager(viewPager, autoRefresh, false);
}
private void setupWithViewPager(@Nullable final ViewPager viewPager, boolean autoRefresh,
boolean implicitSetup) {
final PagerAdapter adapter = viewPager.getAdapter();
if (adapter != null) {
setPagerAdapter(adapter, autoRefresh);
}
}
void setPagerAdapter(@Nullable final PagerAdapter adapter, final boolean addObserver) {
// Finally make sure we reflect the new adapter
populateFromPagerAdapter();
}
void populateFromPagerAdapter() {
removeAllTabs(); //就是这里啦,首先removeAllTabs
if (mPagerAdapter != null) {
final int adapterCount = mPagerAdapter.getCount();
for (int i = 0; i < adapterCount; i++) {
addTab(newTab().setText(mPagerAdapter.getPageTitle(i)), false);
}
// Make sure we reflect the currently set ViewPager item
if (mViewPager != null && adapterCount > 0) {
final int curItem = mViewPager.getCurrentItem();
if (curItem != getSelectedTabPosition() && curItem < getTabCount()) {
selectTab(getTabAt(curItem));
}
}
}
}
复制代码