134

I was playing around with the new android.support.design.widget.TabLayout, and found a problem, in the class definition, there are no methods to change the indicator color, and default height.

Doing some research, found that the default indicator color is taken from the AppTheme. Specifically from here:

<item name="colorAccent">#FF4081</item>

Now, in my case, if I change the colorAccent, it will affect all the other views which uses this value as background color, for example ProgressBar

Now is there any way to change the indicatorColor to other thing besides the colorAccent?

Gabriele Mariotti
  • 320,139
  • 94
  • 887
  • 841
David_E
  • 7,130
  • 4
  • 26
  • 29

12 Answers12

263

Having the problem that the new TabLayout uses the indicator color from the value colorAccent, I decided to dig into the android.support.design.widget.TabLayout implementation, finding that there are no public methods to customize this. However I found this style specification of the TabLayout:

<style name="Base.Widget.Design.TabLayout" parent="android:Widget">
    <item name="tabMaxWidth">@dimen/tab_max_width</item>
    <item name="tabIndicatorColor">?attr/colorAccent</item>
    <item name="tabIndicatorHeight">2dp</item>
    <item name="tabPaddingStart">12dp</item>
    <item name="tabPaddingEnd">12dp</item>
    <item name="tabBackground">?attr/selectableItemBackground</item>
    <item name="tabTextAppearance">@style/TextAppearance.Design.Tab</item>
    <item name="tabSelectedTextColor">?android:textColorPrimary</item>
</style>

Having this style specification, now we can customize the TabLayout like this:

<android.support.design.widget.TabLayout
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@id/pages_tabs"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="?attr/colorPrimary"
    android:minHeight="?attr/actionBarSize"
    android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
    app:tabIndicatorColor="@android:color/white"
    app:tabIndicatorHeight="4dp"/>

And problem solved, both the tab indicator color and height can be changed from their default values.

David_E
  • 7,130
  • 4
  • 26
  • 29
118

With the design support library you can now change them in the xml:

To change the color of the TabLayout indicator:

app:tabIndicatorColor="@color/color"

To change the height of the TabLayout indicator:

app:tabIndicatorHeight="4dp"
Malek Hijazi
  • 4,112
  • 1
  • 26
  • 31
37

Since I can't post a follow-up to android developer's comment, here's an updated answer for anyone else who needs to programmatically set the selected tab indicator color:

tabLayout.setSelectedTabIndicatorColor(Color.parseColor("#FFFFFF"));

Similarly, for height:

tabLayout.setSelectedTabIndicatorHeight((int) (2 * getResources().getDisplayMetrics().density));

These methods were only recently added to revision 23.0.0 of the Support Library, which is why Soheil Setayeshi's answer uses reflection.

Community
  • 1
  • 1
jasonchen2
  • 489
  • 6
  • 7
19
app:tabIndicatorColor="@android:color/white"
Pang
  • 9,564
  • 146
  • 81
  • 122
Sanket Parchande
  • 894
  • 9
  • 14
14

With the desing support library v23 you can set programmatically the color and the height.

Just use for the height:

TabLayout.setSelectedTabIndicatorHeight(int height)

Here the official javadoc.

Just use for the color:

TabLayout.setSelectedTabIndicatorColor(int color)

Here the official javadoc.

Here you can find the info in the Google Tracker.

MathieuMaree
  • 7,453
  • 6
  • 26
  • 31
Gabriele Mariotti
  • 320,139
  • 94
  • 887
  • 841
9

To change indicator color and height programmatically you can use reflection. for example for indicator color use code below:

        try {
            Field field = TabLayout.class.getDeclaredField("mTabStrip");
            field.setAccessible(true);
            Object ob = field.get(tabLayout);
            Class<?> c = Class.forName("android.support.design.widget.TabLayout$SlidingTabStrip");
            Method method = c.getDeclaredMethod("setSelectedIndicatorColor", int.class);
            method.setAccessible(true);
            method.invoke(ob, Color.RED);//now its ok
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }

and to change indicator height use "setSelectedIndicatorHeight" instead of "setSelectedIndicatorColor" then invoke it by your desired height

Mike Ortiz
  • 4,031
  • 4
  • 27
  • 54
Soheil Setayeshi
  • 2,343
  • 2
  • 31
  • 43
  • 1
    Thank you! this helps me! I guess Google forgot to provide method for this in their support library. – Shinta S Jun 18 '15 at 19:03
  • 1
    Why use reflection, if it's already available as public functions? https://developer.android.com/reference/android/support/design/widget/TabLayout.html#setSelectedTabIndicatorColor(int) – android developer Aug 18 '15 at 11:50
  • @SoheilSetayeshi Oh, ok. Thank you. Maybe you should update the answer then. – android developer Aug 19 '15 at 06:52
  • 1
    But this is a perfect solution for APIs below support library 23.0.0. I mean Whaao! Great Answer! – sud007 Jun 09 '16 at 14:50
8

from xml :

app:tabIndicatorColor="#fff"

from java :

tabLayout.setSelectedTabIndicatorColor(Color.parseColor("#FFFFFF"));
tabLayout.setSelectedTabIndicatorHeight((int) (2 * getResources().getDisplayMetrics().density));
Arthur Melo
  • 454
  • 5
  • 13
6

Foto indicator use this:

 tabLayout.setSelectedTabIndicatorColor(ContextCompat.getColor(this, R.color.colorWhite));//put your color
chry
  • 434
  • 7
  • 5
1

You can change this using xml

app:tabIndicatorColor="#fff"
Ishan Fernando
  • 2,758
  • 1
  • 31
  • 38
0

Just put this line in your code. If you change the color then change the color value in parentheses.

tabLayout.setSelectedTabIndicatorColor(Color.parseColor("#FFFFFF"));
saqib javeed
  • 191
  • 2
  • 6
0

Android makes it easy.

public void setTabTextColors(int normalColor, int selectedColor) {
    setTabTextColors(createColorStateList(normalColor, selectedColor));
}

So, we just say

mycooltablayout.setTabTextColors(Color.parseColor("#1464f4"), Color.parseColor("#880088"));

That will give us a blue normal color and purple selected color.

Now we set the height

public void setSelectedTabIndicatorHeight(int height) {
    mTabStrip.setSelectedIndicatorHeight(height);
}

And for height we say

mycooltablayout.setSelectedIndicatorHeight(6);
SmulianJulian
  • 801
  • 11
  • 33
0

If you are trying to use app:tabIndicator="" to set indicator, and using a layer-list drawable as your custom indicator, then you'd better to set app:tabIndicatorColor="" together, because i see this in the source code of TabLayout:

TabLayout.SlidingTabIndicator#draw

If you don't set app:tabIndicatorColor="", then the custom indicator will be drawn with your colorPrimary or colorAccent as the tint color