问题1:
最近在Android8.0上面遇到一个奇葩的事情,就是在布局文件里面设置TabLayout的item,不知为啥,运行起来的时候字体颜色没有显示,以下是没有显示的写法:
<android.support.design.widget.TabLayout android:id="@+id/fragment_transaction_tab" android:layout_width="match_parent" android:layout_height="wrap_content" app:tabIndicatorColor="@color/colorAccent" app:tabIndicatorHeight="@dimen/space_6" app:tabMode="fixed" app:tabSelectedTextColor="@color/colorAccent" app:tabTextAppearance="@style/TabLayoutTextStyle" app:tabTextColor="@color/gray_A4A4A4" > <android.support.design.widget.TabItem android:layout_width="wrap_content" android:layout_height="wrap_content" tools:text="@string/recharge_other" /> <android.support.design.widget.TabItem android:layout_width="wrap_content" android:layout_height="wrap_content" tools:text="@string/recharge_buy" /> </android.support.design.widget.TabLayout>
先不深究,现在说解决办法:直接在代码里面设置就可以了
vTabLayout.addTab(vTabLayout.newTab().setText(getString(R.string.fragment_transaction_self)));
问题2:
Indicator宽度受tabItem的宽度牵制,总感觉Indicator太长不好看,现在要设置自己满意的宽度。
进入TabLayout分析了一下代码,发现里面的tabItem都是添加进SlidingTabStrip这个控件的,其继承LinearLayout
既然是继承LinearLayout这样就好办了,现在的打算是控制tabItem的Margin
做法是:利用反射从TabLayout里面拿到SlidingTabStrip,在从里面获取tabItem
/** * 通过反射获取SlidingTabStrip设置tabItem宽 * * @param tabs * @param leftMargin * @param rightMargin */ public void setIndicator(TabLayout tabs, int leftMargin, int rightMargin) { Class<?> tabLayout = tabs.getClass(); Field tabStrip = null; try { tabStrip = tabLayout.getDeclaredField("mTabStrip"); } catch (NoSuchFieldException e) { LogUtils.d("not found!"); } tabStrip.setAccessible(true); LinearLayout llTab = null; try { llTab = (LinearLayout) tabStrip.get(tabs); } catch (IllegalAccessException e) { LogUtils.d("IllegalAccessException!"); } int left = getResources().getDimensionPixelOffset(leftMargin); int right = getResources().getDimensionPixelOffset(rightMargin); for (int i = 0; i < llTab.getChildCount(); i++) { View child = llTab.getChildAt(i); child.setPadding(0, 0, 0, 0); LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(0, LinearLayout.LayoutParams.MATCH_PARENT, 1); params.leftMargin = left; params.rightMargin = right; child.setLayoutParams(params); child.invalidate(); } }
具体用法:
在布局加载完之后执行下面方法
vTabLayout.post(new Runnable() { @Override public void run() { setIndicator(vTabLayout, R.dimen.space_80, R.dimen.space_80); } });
问题3:
一个不熟悉的用法,现在终于长见识了,TabLayout有这么一段代码
mTabTextAppearance = a.getResourceId(R.styleable.TabLayout_tabTextAppearance, R.style.TextAppearance_Design_Tab); // Text colors/sizes come from the text appearance first final TypedArray ta = context.obtainStyledAttributes(mTabTextAppearance, android.support.v7.appcompat.R.styleable.TextAppearance); try { mTabTextSize = ta.getDimensionPixelSize( android.support.v7.appcompat.R.styleable.TextAppearance_android_textSize, 0); mTabTextColors = ta.getColorStateList( android.support.v7.appcompat.R.styleable.TextAppearance_android_textColor); } finally { ta.recycle(); }
刚开始时一直没有留意ta是关联到mTabTextAppearance的,就以为直接在布局里面用系统属性就能设置字体大小,后来运行了一下发现没有效果,立马去看了一下代码,尴尬,原来是需要通过tabTextAppearance这个属性调用样式才能用到系统的属性
<android.support.design.widget.TabLayout android:id="@+id/fragment_transaction_tab" android:layout_width="match_parent" android:layout_height="wrap_content" app:tabIndicatorColor="@color/colorAccent" app:tabIndicatorHeight="@dimen/space_6" app:tabMode="fixed" app:tabSelectedTextColor="@color/colorAccent" app:tabTextAppearance="@style/TabLayoutTextStyle" app:tabTextColor="@color/gray_A4A4A4" />
<style name="TabLayoutTextStyle"> <item name="android:textSize">@dimen/font_size_28px</item> </style>