Tab không lấy toàn bộ chiều rộng trên thiết bị Máy tính bảng [Sử dụng android.support.design.widget.TabLayout]


203

Tôi có các tab thiết lập là CẬP NHẬT 29/05/2015 bài đăng này . Các tab có chiều rộng đầy đủ trên điện thoại di động Nexus 4 của tôi nhưng trên máy tính bảng nexus 7, nó ở giữa và không bao phủ toàn bộ chiều rộng màn hình.

Ảnh chụp màn hình Nexus 7 Ảnh chụp màn hình Nexus 7 Nexus 4 Nexus 4


đã vật lộn với vấn đề chính xác trong 6 giờ, nhưng tôi không nhận ra nó chỉ có vấn đề với các tab ... nghĩ rằng trên stackoverflow nên có chức năng nâng cấp câu hỏi 10 lần ...
Shirish Herwade

vui lòng thử thêm nhiều thẻ vào câu hỏi ... (vì vậy sẽ hữu ích hơn cho những người như tôi), vì câu hỏi này tôi tìm thấy trên trang thứ ba của danh sách tìm kiếm google của tôi
Shirish Herwade

Câu trả lời:


596

Câu trả lời "đơn giản hơn" được mượn từ Kaizie sẽ chỉ được thêm app:tabMaxWidth="0dp"vào TabLayoutxml của bạn :

<android.support.design.widget.TabLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:tabMaxWidth="0dp"
            app:tabGravity="fill"
            app:tabMode="fixed" />

19
Nếu tôi cần nó có thể cuộn được thì sao? Thay đổi tabMode để hỗ trợ cuộn phá vỡ giải pháp này.
Tiago

3
Bất kỳ giải pháp cho cuộn?
sunlover3

5
Xin chào .. Tôi đã thử thêm điều này. nhưng tab đơn không lấy toàn bộ chiều rộng của bố cục tab.
Surinder

3
Giải pháp này cũng hoạt động nếu tabMode không được đặt. TapMode có thể cuộn không xuất hiện để hỗ trợ các tính năng của trọng lực đầy và chiều rộng tối đa 0dp.
Julio Mendoza

3
Tại sao nó xảy ra mặc dù? Đó có phải là hành vi mặc định? Hoặc một cái gì đó tôi đã không sử dụng tốt? Đây có phải là một phần của hướng dẫn để đặt các tab ở giữa không? Điều này không xảy ra với tôi khi sử dụng hơn 3 tab. Chỉ cho 2 tab.
nhà phát triển Android

91

Tôi đã có cùng một vấn đề và tôi đã kiểm tra kiểu TabLayout và tôi thấy rằng kiểu mặc định của nó là các cách Widget.Design.TabLayouttriển khai khác nhau (bình thường, phong cảnh và sw600dp).

Cái chúng ta cần là cái dành cho máy tính bảng (sw600dp) có cách thực hiện như sau:

<style name="Widget.Design.TabLayout" parent="Base.Widget.Design.TabLayout">
        <item name="tabGravity">center</item>
        <item name="tabMode">fixed</item>
 </style>

Từ kiểu này, chúng tôi sẽ sử dụng " tabGravity " (mà các giá trị có thể là "trung tâm" hoặc "điền") bằng cách sử dụng giá trị "điền".

Nhưng chúng ta cần đi sâu hơn, và sau đó chúng ta thấy rằng cái này mở rộng từ Base.Widget.Design.TabLayoutđó, việc thực hiện là:

<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>

Vì vậy, từ phong cách này, chúng ta sẽ cần ghi đè " tabMaxWidth ". Trong trường hợp của tôi, tôi đặt nó thành 0dp, vì vậy nó không có giới hạn.

Và phong cách của tôi trông như thế này:

<style name="MyTabLayout" parent="Widget.Design.TabLayout">
        <item name="tabGravity">fill</item>
        <item name="tabMaxWidth">0dp</item>
</style>

Và sau đó thanh tab sẽ lấp đầy toàn bộ màn hình từ bên này sang bên kia.


1
khám phá tốt đẹp .. đi đến gốc. Nhưng hãy làm nổi bật câu trả lời chính xác ở trên cùng, sẽ dễ dàng hơn để tìm một người không muốn đọc tất cả câu trả lời
Shirish Herwade

giải pháp tuyệt vời, kỳ lạ làm thế nào api trông giống như bạn có thể kiểm soát nó mà không thay đổi phong cách cơ bản. Có vẻ như tabMaxWidth là thủ phạm thực sự
kandroidj

3
Đây giống như một tập phim của Sherlock. Cảm ơn bạn!!
Lisa Wray

29

Giải pháp cho có thể cuộn: (TabLayout.MODE_SCROLLABLE), đó là khi bạn cần nhiều hơn 2 tab (Tab động)

Bước 1: style.xml

<style name="tabCustomStyle" parent="Widget.Design.TabLayout">
            <item name="tabGravity">fill</item>
            <item name="tabMaxWidth">0dp</item>
            <item name="tabIndicatorColor">#FFFEEFC4</item>
            <item name="tabIndicatorHeight">2dp</item>
            <item name="tabTextAppearance">@style/MyCustomTabTextAppearance</item>
            <item name="tabSelectedTextColor">#FFFEEFC4</item>
        </style>

        <style name="MyCustomTabTextAppearance" parent="TextAppearance.Design.Tab">
            <item name="android:textSize">@dimen/tab_text_size</item>
            <item name="android:textAppearance">@style/TextAppearance.roboto_medium</item>
            <item name="textAllCaps">true</item>
        </style>
        <style name="TextAppearance.roboto_medium" parent="android:TextAppearance">
            <item name="android:fontFamily">sans-serif-medium</item>
        </style>

Bước 2: Bố cục xml của bạn

<android.support.design.widget.TabLayout
            android:id="@+id/sliding_tabs"
            style="@style/tabCustomStyle"
            android:layout_width="match_parent"
            android:layout_height="@dimen/tab_strip_height"
            android:background="@color/your_color"
            app:tabMode="scrollable"
            app:tabTextColor="@color/your_color" />

Bước 3: Trong Activity / Fragment của bạn, nơi bạn có các tab.

/**
     * To allow equal width for each tab, while (TabLayout.MODE_SCROLLABLE)
     */
    private void allotEachTabWithEqualWidth() {

        ViewGroup slidingTabStrip = (ViewGroup) mTabLayout.getChildAt(0);
        for (int i = 0; i < mTabLayout.getTabCount(); i++) {
            View tab = slidingTabStrip.getChildAt(i);
            LinearLayout.LayoutParams layoutParams = (LinearLayout.LayoutParams) tab.getLayoutParams();
            layoutParams.weight = 1;
            tab.setLayoutParams(layoutParams);
        }

    }

Điều này chỉ hoạt động với nhiều hơn 1 tab, nếu chúng ta chỉ có một tab thì tab không lấp đầy bố cục tab. Để giải quyết vấn đề đó, tôi đã thêm ứng dụng: tabMaxWidth = "1000dp" và nó đã hoạt động.
jzeferino

Điều này làm việc tốt nhất cho tôi. Trong lớp bố trí tab tùy chỉnh của tôi, tôi áp đảo addTabvà đặt trọng số cho mỗi tab khi nó được thêm vào. override fun addTab(tab: Tab, position: Int, setSelected: Boolean) { super.addTab(tab, position, setSelected) allotEachTabWithEqualWidth() }
Justin Lee

15

Để buộc các tab chiếm hết chiều rộng (chia thành các kích thước bằng nhau), áp dụng các cách sau cho TabLayoutchế độ xem:

TabLayout tabLayout = (TabLayout) findViewById(R.id.your_tab_layout);
tabLayout.setTabGravity(TabLayout.GRAVITY_FILL);
tabLayout.setTabMode(TabLayout.MODE_FIXED);

2
Chỉ cần cho mọi người biết, điều này không hoạt động nếu bạn TabLayoutđược đặt thành app:tabMode=“scrollable”, điều đó sẽ dẫn đến các tab trở thành độ dài cố định (các từ dài sẽ bao bọc) và các tab sẽ không còn trượt nữa, về cơ bản làm cho các tab cố định lại một lần nữa.
Sakiboy

5

Điều này hữu ích bạn phải thử

 <android.support.design.widget.TabLayout
        android:id="@+id/tabs"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:tabMaxWidth="0dp"
        app:tabGravity="fill"
        app:tabMode="fixed"
        app:tabIndicatorColor="@color/white"
        app:tabSelectedTextColor="@color/white"
        app:tabTextColor="@color/orange" />

4
<android.support.design.widget.TabLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:tabMaxWidth="0dp"
            app:tabGravity="fill"
            app:tabMode="fixed" />

làm việc cho tôi. Cái này cũng cóxmlns:app="http://schemas.android.com/apk/res-auto"


3

Đối với tôi mã sau đây đã làm việc và là đủ.

<android.support.design.widget.TabLayout
        android:id="@+id/tabs"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        app:tabGravity="fill"/>

2

Kiểm tra mã dưới đây cho các giải pháp.

Dưới đây là mã bố trí:

<com.yourpackage.CustomTabLayout
    android:id="@+id/tabs"
    android:layout_width="match_parent"
    android:layout_height="?attr/actionBarSize"
    android:background="@color/off_white"
    app:tabIndicatorColor="@color/primaryColor"
    app:tabIndicatorHeight="3dp"
    app:tabMode="scrollable"
    app:tabPaddingEnd="0dp"
    app:tabPaddingStart="0dp" />

Lưu ý, đối với số lượng tab động, đừng quên gọi setTabNumbers (tabcount).

import android.content.Context;
import android.support.design.widget.TabLayout;
import android.util.AttributeSet;
import android.util.
import java.lang.reflect.Field;

public class CustomTabLayout extends TabLayout
{
    private static final int WIDTH_INDEX = 0;
    private int DIVIDER_FACTOR = 3;
    private static final String SCROLLABLE_TAB_MIN_WIDTH = "mScrollableTabMinWidth";

    public CustomTabLayout(Context context) {
        super(context);
        initTabMinWidth();
    }

    public CustomTabLayout(Context context, AttributeSet attrs) {
        super(context, attrs);
        initTabMinWidth();
    }

    public CustomTabLayout(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        initTabMinWidth();
    }

    public void setTabNumbers(int num)
    {
        this.DIVIDER_FACTOR = num;
        initTabMinWidth();
    }

    private void initTabMinWidth()
    {
        int[] wh = getScreenSize(getContext());
        int tabMinWidth = wh[WIDTH_INDEX] / DIVIDER_FACTOR;

        Log.v("CUSTOM TAB LAYOUT", "SCREEN WIDTH = " + wh[WIDTH_INDEX] + " && tabTotalWidth = " + (tabMinWidth*DIVIDER_FACTOR) + " && TotalTabs = " + DIVIDER_FACTOR);

        Field field;
        try {
            field = TabLayout.class.getDeclaredField(SCROLLABLE_TAB_MIN_WIDTH);
            field.setAccessible(true);
            field.set(this, tabMinWidth);
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private static final int WIDTH_INDEX = 0;
    private static final int HEIGHT_INDEX = 1;

    public static int[] getScreenSize(Context context) {
        int[] widthHeight = new int[2];
        widthHeight[WIDTH_INDEX] = 0;
        widthHeight[HEIGHT_INDEX] = 0;

        try {
            WindowManager windowManager = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
            Display display = windowManager.getDefaultDisplay();

            Point size = new Point();
            display.getSize(size);
            widthHeight[WIDTH_INDEX] = size.x;
            widthHeight[HEIGHT_INDEX] = size.y;

            if (!isScreenSizeRetrieved(widthHeight))
            {
                DisplayMetrics metrics = new DisplayMetrics();
                display.getMetrics(metrics);
                widthHeight[0] = metrics.widthPixels;
                widthHeight[1] = metrics.heightPixels;
            }

            // Last defense. Use deprecated API that was introduced in lower than API 13
            if (!isScreenSizeRetrieved(widthHeight)) {
                widthHeight[0] = display.getWidth(); // deprecated
                widthHeight[1] = display.getHeight(); // deprecated
            }
        } catch (Exception e) {
            e.printStackTrace();
        }

        return widthHeight;
    }

    private static boolean isScreenSizeRetrieved(int[] widthHeight) {
        return widthHeight[WIDTH_INDEX] != 0 && widthHeight[HEIGHT_INDEX] != 0;
    }
}

Tham chiếu được lấy từ https://medium.com/@elsenovraditya/set-tab-minimum-ference-of-scrollable-tablayout-programmatically-8146d6101efe


2

Giải pháp cho cuộn (Kotlin)

Trong xml:

     <com.google.android.material.tabs.TabLayout
            android:id="@+id/home_tab_layout"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:tabMaxWidth="0dp"
            app:tabMode="scrollable"
            android:fillViewport="true"
            app:tabGravity="fill" />

Trong Kotlin:

Trong trường hợp của tôi nếu ít hơn 3 tab tôi phân bổ không gian bằng nhau.

Lưu ý: Nếu điều kiện theo yêu cầu của bạn

        if(list.size <= 3){
          allotEachTabWithEqualWidth(your_tab_layout)
        }

     fun allotEachTabWithEqualWidth(tabLayout: TabLayout) {
        mTabLayout.tabMode=  TabLayout.MODE_FIXED
        val slidingTabStrip = tabLayout.getChildAt(0) as ViewGroup
        for (i in 0 until tabLayout.getTabCount()) {
            val tab = slidingTabStrip.getChildAt(i)
            val layoutParams = tab.layoutParams as LinearLayout.LayoutParams
            layoutParams.weight = 1f
            tab.layoutParams = layoutParams
        }

    }

1

Tại sao tất cả công việc bận rộn đó? Chỉ cần đặt app:tabMode="scrollable"TabLayout của bạn vào XML. Đó là nó.

nhập mô tả hình ảnh ở đây


1
Nếu có 3 tab thì sao? không phù hợp với màn hình (các tab động xuất phát từ API máy chủ) số lượng tab được biết đến vào thời gian chạy ..
Ram Prakash Bhat

Sau đó, bạn thậm chí có thể thiết lập chương trình như thế này tabLayout.setTabMode(TabLayout.MODE_SCROLLABLE);Ngoài ra đây chỉ là một thuộc tính để đặt cho tabLoutout, điều này không bao giờ quan trọng bạn có thêm bao nhiêu tab tĩnh hay động.
Ali Akram

Nó sẽ làm cho chiều rộng của tab theo kích thước văn bản. Kiểm tra câu trả lời đã chỉnh sửa của tôi bằng hình ảnh.
Ali Akram

Ya trong chế độ tab trường hợp đó là SCROLLABLE, cuối cùng, bạn sẽ thấy khoảng trống trông kỳ lạ
Ram Prakash Bhat

1

Trong biến thể của vấn đề này, tôi có 3 tab có kích thước vừa phải, không chiếm hết chiều rộng trên máy tính bảng. Tôi không cần các tab để có thể cuộn trên máy tính bảng, vì máy tính bảng đủ lớn để hiển thị tất cả các tab cùng nhau mà không cần cuộn. Nhưng tôi đã cần các tab để có thể cuộn trên điện thoại, vì điện thoại quá nhỏ để hiển thị tất cả các tab với nhau.

Giải pháp tốt nhất trong trường hợp của tôi là thêm một res/layout-sw600dp/main_activity.xmltệp, trong đó TabLayout có liên quan có thể có app:tabGravity="fill"app:tabMode="fixed". Nhưng trong thường xuyên của tôi res/layout/main_activity.xml, tôi đã bỏ đi app:tabGravity="fill"app:tabMode="fixed", và app:tabMode="scrollable"thay vào đó.


-1

Xin lưu ý rằng bạn cũng cần phải thiết lập

  app:tabPaddingStart="-1dp"
  app:tabPaddingEnd="-1dp"

để lấp đầy không gian


Chào mừng bạn đến với Stack Overflow. Hãy đi tham quan . Đây là một trang web câu hỏi và câu trả lời, không phải là một diễn đàn thảo luận. Phần này chỉ dành cho câu trả lời đầy đủ. Khi bạn đã kiếm được 50 điểm danh tiếng bằng cách hỏi và trả lời, bạn sẽ có thể nhận xét về câu hỏi và câu trả lời của người dùng khác .
Chris
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.