Sparks Sparks - 2 months ago 13
Android Question

Are label and icon mutually exclusive in a TabHost TabSpec setIndicator?

On an Android app (min sdk 11, target sdk 18), a class which extends Fragment ought to create the TabHost tabs (TabSpec) with one label AND one icon. But...

TabSpec ts1;
// if the label is set to "Home", the label is displayed but not the image
ts1 = tab_host.newTabSpec("TAB_ONE").setIndicator("Home", getActivity().getResources().getDrawable(R.drawable.ic_tabone)).setContent(R.id.edit_species_tab);

// if the label is null or empty, the image is displayed
ts1 = tab_host.newTabSpec("TAB_ONE").setIndicator(null, getActivity().getResources().getDrawable(R.drawable.ic_tabone)).setContent(R.id.edit_species_tab);


As far as I can see the documentation does not mention that the label and the icon are mutually exclusive.

At first I thought that the label had a solid background colour hiding the icon, but this is not the case. In fact, when I set the TabHost background I can see that the label is transparent:

tab_host.getTabWidget().setBackgroundResource(R.drawable.ic_mybackground);


How can I set the TabSpec background so that both the label AND the icon are displayed for each tab?

tab_host.xml



<TabWidget
android:id="@android:id/tabs"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom" />

<FrameLayout
android:id="@android:id/tabcontent"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:paddingTop="65dp" >

<LinearLayout
android:id="@+id/edit_species_tab"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:padding="5dp" >
</LinearLayout>

<LinearLayout
android:id="@+id/edit_regions_tab"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:padding="5dp" >
</LinearLayout>

<LinearLayout
android:id="@+id/edit_quiz_tab"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:padding="5dp" >
</LinearLayout>

<LinearLayout
android:id="@+id/edit_about_tab"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical"
android:padding="5dp" >
</LinearLayout>
</FrameLayout>



Answer

In holo theme, the tab only support label or icon and mutually exclusive.

After Holo, as a default the tab supposed only have label, please check the design guideline. http://developer.android.com/design/building-blocks/tabs.html

If you willing to both label & icon at the same time, there are two options.

Option 1: Using old Gingerbread theme. Set your android:targetSdkVersion 9 or below. (Before Honeycomb)

Option 2: Using custom layout & view for your tab. Of course, it required some efforts, but you can use any custom layout what you want. For example:

in your activity code:

    TabHost.TabSpec ts1;
    View tabView = getLayoutInflater().inflate(R.layout.custom_tab, tab_host, false);
    ts1 = tab_host.newTabSpec("TAB_ONE").setIndicator(tabView).setContent(R.id.edit_species_tab);

in your layout: (whatever you want)

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/tab"
android:layout_width="80dp"
android:layout_height="wrap_content"
android:orientation="vertical">
<TextView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Hello"
    />
<ImageView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_launcher"
    />
</LinearLayout>