Могу ли я использовать стиль вкладки по умолчанию в моем пользовательском представлении вкладок? - PullRequest
11 голосов
/ 25 ноября 2011

Моя основная деятельность - TabActivity, но мои вкладки не требуют значков. Я знаю, что могу опустить значок, используя перегруженный метод TabHost.TabSpec.setIndicator(CharSequence label), как ответили в на этот вопрос .

Но место, куда должен идти значок, все еще зарезервировано, поэтому много места теряется. Это уже отмечалось в этом вопросе . Кажется, я не могу просто уменьшить высоту вкладки. Мне придется снабдить свой собственный View перегрузкой TabHost.TabSpec.setIndicator(View view).

Отлично, но я хочу убедиться, что остальная часть стиля (фон / цвет) остается одинаково «android» на всех устройствах, как если бы я использовал индикатор вкладки по умолчанию. Поэтому я не хочу указывать свои цвета.

Я нашел @android:color/tab_indicator_text, и использование его для цвета текста TextView работает, как и ожидалось. Но я не знаю, где взять стандартные цвета фона вкладки. Я также обнаружил стиль @android:style/Widget.TabWidget, но применение его ни к TextView, ни к окружающему LinearLayout, похоже, не поможет.

Это xml-файл вида индикатора вкладки, взятый из некоторого учебника:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/tabLayout"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:gravity="center"
    android:padding="12dip" >

    <TextView
        android:id="@+id/tabText"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:textColor="@android:color/tab_indicator_text" />
</LinearLayout>

Как мне настроить стиль вкладки "Android по умолчанию" на этом?


Редактировать: Далее я попытался добавить вкладку по умолчанию с помощью setIndicator(CharSequence), взять getBackground отрисовку его представления индикатора, очистить все вкладки, добавить мои пользовательские представления (см. Выше), затем Поместите найденный мной чертеж в setBackground для новых индикаторов.

Результат выглядит как правильный и неправильный. Во-первых, они снова слишком высоки, поэтому я ничего не получил. С другой стороны, фоновые состояния всех вкладок теперь каким-то образом связаны (активны, выделены, выделены и т. Д.). Использование mutate() для рисования не помогло вообще. Следующий трюк: я добавил три вкладки по умолчанию, взял все их фоны, очистил их и дал своим собственным трем вкладкам по одному фону в каждой.

Ну, это решает вторую проблему. Их состояния больше не связаны. Но они все еще слишком высоки. Поэтому я уменьшил высоту TabWidget, используя updateViewLayout. Это работает, но оставляет обесцвеченную полосу в верхней части вкладки индикаторов.

На самом деле, я просто получаю ту же ситуацию, что и при использовании метода TabHost.TabSpec.setIndicator(CharSequence label). И вообще, все эти хаки заставляют меня чувствовать себя грязным. Разве не существует элегантного способа получить стиль Android по умолчанию в пользовательском представлении?

Ответы [ 5 ]

10 голосов
/ 12 декабря 2011

Этот код взят из Android-источников tab_indicator.xml

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="0dip"
    android:layout_height="64dip"
    android:layout_weight="1"
    android:layout_marginLeft="-3dip"
    android:layout_marginRight="-3dip"
    android:orientation="vertical"
    android:background="@android:drawable/tab_indicator">

    <ImageView android:id="@+id/icon"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
    />

    <TextView android:id="@+id/title"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:layout_centerHorizontal="true"
        style="?android:attr/tabWidgetStyle"
    />

</RelativeLayout>

Вы можете просто взять этот код, удалить ImageView, изменить layout_centerHorizontal в TextView на layout_center, уменьшить высоту RelativeLayout и предоставить этот вид в TabHost.TabSpec.setIndicator(View view). Есть ссылки только на @android ресурсы, поэтому вам не нужно создавать какие-либо рисованные или текстовые стили.

EDIT

Стандартный Android-фон для рисования индикатора вкладки не виден в приложении, но это можно сделать так:

TabSpec tc = getTabHost().newTabSpec("tag");
tc.setIndicator("indicator1");
tc.setContent(content);
getTabHost().addTab(tc);
getTabHost().findViewById(android.R.id.icon).setVisibility(View.GONE);
TextView tv = (TextView) getTabHost().findViewById(android.R.id.title);
RelativeLayout.LayoutParams rllp = new RelativeLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
rllp.addRule(RelativeLayout.CENTER_IN_PARENT);
tv.setLayoutParams(rllp);

Тогда можно уменьшить высоту вкладок:

RelativeLayout parent = ((RelativeLayout) tv.getParent());
ViewGroup.LayoutParams vglp = parent.getLayoutParams();
vglp.height = android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
parent.setLayoutParams(vglp);

Результат будет: this

2 голосов
/ 08 декабря 2011

Я думаю, что лучшим вариантом было бы настроить аспект «Вкладки», используя xml-файлы, называемые селекторами (которые вы поместите в свою папку «drawable»), пользовательский tab_indicator.xml в папке «layout», стиль для текстаи тема, использующая такой стиль.

Это файл tab_indicator_selector.xml, который находится в папке «drawable» и требуется для tab_indicator.xml:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <!-- Non focused states ... -->
    <!-- Focused states ... -->
    <!-- Pressed -->
    <item android:state_selected="true" android:state_pressed="true"    android:drawable="@drawable/tab_pressed" />
    <item android:state_pressed="true" android:drawable="@drawable/tab_pressed" />
</selector>

И это нажатие tab_pressedСелектор состояния .xml:

<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:top="53dp">
        <shape android:shape="rectangle">
            <solid android:color="@color/white" />
        </shape>
    </item>
    <item android:top="53dp" android:bottom="1dp">
        <shape android:shape="rectangle">
            <solid android:color="@color/white" />
        </shape>
    </item>
    <item android:left="2dp" android:right="2dp"> 
        <shape android:shape="rectangle">
            <gradient android:angle="90" 
                android:startColor="@color/black"
                android:endColor="@color/white" />
            <stroke android:width="2dp" android:color="@color/red" />
        </shape>
    </item>
</layer-list>

Другие состояния могут быть достигнуты путем создания tab_focused.xml, tab_selected.xml и tab_unseleceted.xml и установки правильных комбинаций android: state_XXX.

Tab_indicatorвыглядит так:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="0dip" 
    android:layout_height="52dip" <!-- Control the height of the Tab here! -->
    android:layout_weight="1"
    android:orientation="vertical"
    android:background="@drawable/tab_indicator_selector" 
    android:layout_marginTop="2dp"
    android:padding="2dp">

   <!-- Generally here goes an ImageView, but you said you don't want it. -->

    <TextView android:id="@+id/tab_title"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" 
        android:textSize="11dp" 
        android:textStyle="bold" 
        android:layout_alignParentBottom="true"
        android:layout_centerHorizontal="true"
        style="?android:attr/tabWidgetStyle"
    />    
</RelativeLayout>

На стороне реализации должен выглядеть так:

private void setTabs(){
    tabHost = getTabHost();
    addTab(R.string.tab_title_something, R.drawable.tab_something_selector, new Intent().setClass(this, PlacesNearbyTab.class));
}

private void addTab(int labelId, int drawableId, Intent intent) {
    TabHost.TabSpec spec = tabHost.newTabSpec("tab" + labelId);
    View tabIndicator = LayoutInflater.from(this).inflate(R.layout.tab_indicator, getTabWidget(), false);
    TextView title = (TextView) tabIndicator.findViewById(R.id.tab_title);
    title.setText(labelId);
    spec.setIndicator(tabIndicator);
    spec.setContent(intent);
    tabHost.addTab(spec);

}

Надеюсь, это поможет.Это долгое решение, но использование тем и стилей довольно удобно, когда приложение выросло или когда вы хотите изменить его внешний вид в версии 2.

Наконец, я предлагаю вам ознакомиться с новым SDKверсия 14 и тема Холо.Вкладки на Holo предназначены как для планшетов, так и для телефонов, и вы можете сделать их с иконками и без них.

0 голосов
/ 13 декабря 2011

Вы можете найти файлы res color для каждой платформы в / path-to-android-sdk / platform /, и вы можете использовать @android: style / или @android: color / для доступа к ресурсам по умолчанию из XML ...

Но, как вы упомянули, вы знаете, что цвета и стили TabWidgets и других представлений пользовательского интерфейса Android меняются от версии к версии и между марками устройств.

Даже если вы можете делать то, что хотите, ваши вкладки будут выглядеть по-разному в зависимости от версии и марки устройства ... что не является обычным.

Я бы реализовал свои собственные стили табуляции с помощью одного из предложенных решений. Удачи тебе!

0 голосов
/ 12 декабря 2011

не могли бы вы попробовать следующий пример кода, который взят из default tab_indicator.xml и внести небольшое изменение в соответствии с описанным вами требованием.Спасибо!

<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="0dip"
android:layout_height="64dip"
android:layout_weight="1"
android:layout_marginLeft="-3dip"
android:layout_marginRight="-3dip"
android:gravity="center"
android:background="@android:drawable/tab_indicator">

    <TextView
        android:id="@+id/title"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        style="?android:attr/tabWidgetStyle">
    </TextView>

</LinearLayout>
0 голосов
/ 07 декабря 2011

Я не уверен, что это отцентрирует текст, но вы можете изменить высоту вкладки, не изменяя фон Android по умолчанию.

Попробуйте это:

TabHost tabs = //initialize your TabHost here
tabs.setup();
TabSpec tspec1 = tabs.newTabSpec("First Tab");
tspec1.setIndicator("Actions");
tabs.addTab(tspec1);


tabs.getTabWidget.getChildAt(0).getLayoutParams().height = (int) (35 * 1.5);

Где 35 - высота в пикселях, а умножение на 1,5 делает высоту 35dp.

Удачи.

...