簡體   English   中英

Android:如何在工具欄中居中標題

[英]Android: How to Center title in ToolBar

我第一次在我的項目中使用 ToolBar,所以我不知道如何在 android 中自定義工具欄。 我需要將標題居中到工具欄,請告訴我如何做到這一點。

預先感謝。

簡單地在工具欄對齊中心添加 TextView 的問題是在工具欄中添加菜單項,這將偏移居中的文本。

為了解決這個問題,我將文本分層放在工具欄的頂部,而不是里面。 這樣不管你添加多少圖標,它都不會偏移居中的文本:

<android.support.design.widget.AppBarLayout
    android:id="@+id/appbar_layout"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">
    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content">

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:theme="@style/ThemeOverlay.AppCompat.ActionBar">
        </android.support.v7.widget.Toolbar>

        <TextView
            android:layout_centerInParent="true"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="@string/app_name"/>

    </RelativeLayout>
</android.support.design.widget.AppBarLayout>

這樣就不需要任何額外的邏輯來補償工具欄上后退按鈕/溢出菜單/搜索圖標等的偏移間距,因為居中的文本在它上面,而不是在它里面。

請記住, Toolbar和其他Toolbar一樣只是一個ViewGroup 所以你可以把View塞進去。 在您的情況下,您需要一個Toolbar內的TextView

<android.support.v7.widget.Toolbar
    android:id="@+id/toolbar"
    android:layout_height="wrap_content"
    android:layout_width="match_parent">

    <TextView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:text="Some Fancy Title"
        android:gravity = "center"
        android:id="@+id/toolbar_title" />

</android.support.v7.widget.Toolbar>

現在,首先檢索它,然后使用setSupportActionBar()Toolbar設置為您的操作欄。

由於TextView的重力設置為center ,因此文本必須居中。

您可以通過包裝標題和水平右填充來強制工具欄居中,該右填充具有標題的默認左填充。 然后將背景顏色添加到工具欄的父級,這樣通過包裝標題切出的部分顏色相同(在我的示例中為白色):

<android.support.design.widget.AppBarLayout
    android:id="@+id/appbar_layout"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="@color/white">

            <android.support.v7.widget.Toolbar
               android:id="@+id/toolbar"
               android:layout_width="wrap_content"
               android:layout_height="56dp"
               android:layout_gravity="center_horizontal"
               android:paddingEnd="15dp"
               android:paddingRight="15dp"
               android:theme="@style/ThemeOverlay.AppCompat.ActionBar"
               app:titleTextColor="@color/black"/>

</android.support.design.widget.AppBarLayout>

ToolBar 是一個視圖組。 所以要居中對齊文本使用

app_bar.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.Toolbar xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res/in.chabu"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="?attr/colorPrimary"
    app:theme="@style/ToolBarTheme" 
    android:minHeight="?attr/actionBarSize">

     <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="@string/title_activity_sign_up"
        android:layout_gravity="center"
        android:id="@+id/toolbar_title" 
        android:textStyle="bold"
        android:textColor="@android:color/white"/>

</android.support.v7.widget.Toolbar>

活動注冊

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="in.chabu.activities.SignUpActivity" >

    <include 
        android:id="@+id/tool_bar"
        layout="@layout/app_bar"/>

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@+id/tool_bar"
        android:text="@string/hello_world" />

</RelativeLayout>

活動

public class SignUpActivity extends ActionBarActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_sign_up);

        Toolbar toolbar = (Toolbar) findViewById(R.id.tool_bar);

        setSupportActionBar(toolbar);

        getSupportActionBar().setDisplayShowTitleEnabled(false);
    }


}

僅在Toolbar放置另一個TextView不足以使標題相對於屏幕居中,其位置將取決於工具欄中的其他項目(后退按鈕、菜單項)。

要使標題居中,您可以手動設置其位置:

擴展android.support.v7.widget.Toolbar類並進行以下更改:

  1. 添加TextView
  2. 覆蓋onLayout()並將TextView位置設置為居中( titleView.setX((getWidth() - titleView.getWidth())/2)
  3. 覆蓋setTitle() ,其中將標題文本設置為新的文本視圖
public class CenteredToolbar extends Toolbar {

        private TextView titleView;

        public CenteredToolbar(Context context) {
            this(context, null);
        }

        public CenteredToolbar(Context context, @Nullable AttributeSet attrs) {
            this(context, attrs, android.support.v7.appcompat.R.attr.toolbarStyle);
        }

        public CenteredToolbar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
            super(context, attrs, defStyleAttr);

            titleView = new TextView(getContext());

            int textAppearanceStyleResId;
            TypedArray a = context.getTheme().obtainStyledAttributes(attrs,
                    new int[] { android.support.v7.appcompat.R.attr.titleTextAppearance }, defStyleAttr, 0);
            try {
                textAppearanceStyleResId = a.getResourceId(0, 0);
            } finally {
                a.recycle();
            }
            if (textAppearanceStyleResId > 0) {
                titleView.setTextAppearance(context, textAppearanceStyleResId);
            }

            addView(titleView, new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));
        }

        @Override
        protected void onLayout(boolean changed, int l, int t, int r, int b) {
            super.onLayout(changed, l, t, r, b);
            titleView.setX((getWidth() - titleView.getWidth())/2);
        }

        @Override
        public void setTitle(CharSequence title) {
            titleView.setText(title);
        }
    }

在布局中,您可以像這樣使用此類:

<com.example.CenteredToolbar xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/toolbar"
    android:layout_width="match_parent"
    android:layout_height="?attr/actionBarSize"
    android:background="?attr/colorPrimary"
    android:elevation="4dp"
    android:theme="@style/ToolbarTheme"/>

此外,要使新標題文本看起來像標准標題,您應該將titleTextAppearance樣式應用於新的TextView ( titleView.setTextAppearance(context, textAppearanceStyleResId) )。

最終的用戶界面如下所示: 在此處輸入圖片說明 對於我的項目,我在左側有導航圖標,在右側有菜單(超過 1 個),並且希望將標題放在中間。

我有setSupportActionBar(toolbar)_actionBar.setCustomView(R.layout.actionbar_filter); . 我的布局文件:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
                android:id="@+id/lib_action_bar_filter_view_layout"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:background="?attr/selectableItemBackgroundBorderless"
                android:gravity="center">

    <TextView
        android:id="@id/lib_action_bar_filter_view"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:gravity="center"
        android:maxLines="2"
        android:paddingLeft="5dp"
        android:paddingRight="5dp"
        android:textColor="@android:color/white"
        android:textSize="15sp"/>

</RelativeLayout>

我的工具欄擴展了 android.support.v7.widget.Toolbar,然后(一種硬代碼)測量 RelativeLayout 的大小,最后將其布局在水平中心。

/**
 * Customized the <code>RelativeLayout</code> inside the <code>Toolbar</code>.
 * Because by default the custom view in the <code>Toolbar</code> cannot set
 * width as our expect value. So this class allows setting the width of the
 * <code>RelativeLayout</code> to take up any percentage of the screen width.
 */
public class CenteredToolbar extends Toolbar {

private static final double WIDTH_PERCENTAGE = 0.8;

private TextView titleView;

public CenteredToolbar(Context context) {
    this(context, null);
}

public CenteredToolbar(Context context, @Nullable AttributeSet attrs) {
    this(context, attrs, android.support.v7.appcompat.R.attr.toolbarStyle);
}

public CenteredToolbar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
    super(context, attrs, defStyleAttr);
}

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    super.onMeasure(widthMeasureSpec, heightMeasureSpec);
    int childCount = getChildCount();
    for (int i = 0; i < childCount; i++) {
        View view = this.getChildAt(i);
        if (view instanceof RelativeLayout) {
            int width = getMeasuredWidth();
            ViewGroup.LayoutParams layoutParams = view.getLayoutParams();
            layoutParams.width = (int) (width * WIDTH_PERCENTAGE);
            view.setLayoutParams(layoutParams);
            break;
        }
    }
}

@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
    super.onLayout(changed, l, t, r, b);
    int childCount = getChildCount();
    for (int i = 0; i < childCount; i++) {
        View view = this.getChildAt(i);
        if (view instanceof RelativeLayout) {
            forceTitleCenter(view);
            break;
        }
    }
}

/**
 * Centering the layout.
 *
 * @param view The view to be centered
 */
private void forceTitleCenter(View view) {
    int toolbarWidth = getMeasuredWidth();
    int relativeLayoutWidth = view.getMeasuredWidth();
    int newLeft = (int) (toolbarWidth - relativeLayoutWidth) / 2;
    int top = view.getTop();
    int newRight = newLeft + relativeLayoutWidth;
    int bottom = view.getBottom();
    view.layout(newLeft, top, newRight, bottom);
}
}

附上我的工具欄布局。 也許你不需要這個,我只是貼在這里供別人參考:

<?xml version="1.0" encoding="utf-8"?>
<com.chinalwb.CenteredToolbar
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/vmosolib_toolbar"
    android:layout_width="match_parent"
    android:layout_height="?attr/actionBarSize"
    android:background="?attr/colorPrimary"
    android:elevation="4dp"
    app:contentInsetEnd="0dp"
/>

當你有 Home 或 Up 按鈕和居中的標題,並且標題不再居中並且稍微向右移動一點時,將你的 textview 設置為 width=wrap_content 和 layout_gravity=center

<TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center"/>

我稍微修改了Toolbar源,使標題中心對齊。

public class CenterTitleToolbar extends Toolbar {
    private AppCompatTextView titleTextView;


    public CenterTitleToolbar(Context context) {
        super(context);
    }

    public CenterTitleToolbar(Context context, @Nullable AttributeSet attrs) {
        super(context, attrs);
    }

    public CenterTitleToolbar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    @Override
    public void setTitle(CharSequence title) {
        if (!TextUtils.isEmpty(title)) {
            if (titleTextView == null) {
                final Context context = getContext();
                titleTextView = new AppCompatTextView(context);
                titleTextView.setSingleLine();
                titleTextView.setEllipsize(TextUtils.TruncateAt.END);
                titleTextView.setTextAppearance(context, R.style.TextAppearance_MaterialComponents_Headline6);
                final LayoutParams lp = generateDefaultLayoutParams();
                lp.gravity = Gravity.CENTER;
                titleTextView.setLayoutParams(lp);
            }
            if (titleTextView.getParent() != this) {
                addSystemView(titleTextView);
            }
        } else if (titleTextView != null && titleTextView.getParent() == this) {
            removeView(titleTextView);
        }
        if (titleTextView != null) {
            titleTextView.setText(title);
        }
    }

    private void addSystemView(View v) {
        final ViewGroup.LayoutParams vlp = v.getLayoutParams();
        final LayoutParams lp;
        if (vlp == null) {
            lp = generateDefaultLayoutParams();
        } else if (!checkLayoutParams(vlp)) {
            lp = generateLayoutParams(vlp);
        } else {
            lp = (LayoutParams) vlp;
        }
        addView(v, lp);
    }

}

文本樣式TextAppearance_MaterialComponents_Headline6包含在新的Android 材料庫中

您可以使用MaterialToolbar ,它支持 android material:1.4.0-alpha02

https://github.com/material-components/material-components-android/commit/cbf528e3a6deaa2bc39d0836b3a850b27c2ada49

    implementation 'com.google.android.material:material:1.4.0-alpha02'
<com.google.android.material.appbar.MaterialToolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            app:titleCentered="true" />

基於@LiuWenbin_NO,

我創建了一個自定義工具欄,它不需要任何額外的視圖來在 textview 中居中標題,

import android.content.Context
import android.util.AttributeSet
import android.widget.TextView
import androidx.appcompat.widget.Toolbar
import android.view.Gravity

class CenteredToolbar(context: Context, attrs: AttributeSet?, defStyleAttr: Int):
Toolbar(context, attrs, defStyleAttr) {

constructor(context: Context) : this(context, null, 0)

constructor(context: Context, attrs: AttributeSet) : this(context, attrs, androidx.appcompat.R.attr.toolbarStyle)

override fun onLayout(changed: Boolean, l: Int, t: Int, r: Int, b: Int) {
    super.onLayout(changed, l, t, r, b)

    val childCount = childCount
    for (i in 0 until childCount) {
        val view = this.getChildAt(i)
        if (view is TextView) {
            forceTitleCenter(view,l, r)
            break
        }
    }
}

/**
 * Centering the layout.
 *
 * @param view The view to be centered
 */
private fun forceTitleCenter(view: TextView, l: Int,  r: Int) {
    val top = view.getTop()
    val bottom = view.getBottom()
    view.layout(l, top, r, bottom)
    navigationIcon?.let{
        view.setPadding(it.intrinsicWidth,0,0,0)
    }
    view.gravity = Gravity.CENTER
}

}

 <ui.customView.CenteredToolbar
                android:id="@+id/apd_toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="?attr/colorPrimary"
                app:navigationIcon="@drawable/ic_search"
                app:title="Check Title"
                app:elevation="4dp"/>

就工具欄而言,是一個視圖組,因此您可以在其中創建布局。 按着這些次序

1-在您的工具欄中創建一個 textview 2-使您的 textview 重心

    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_width="match_parent"
        android:layout_height="?attr/actionBarSize"
        android:background="?attr/colorPrimary"
        app:popupTheme="@style/AppTheme.PopupOverlay" >

        <de.hdodenhof.circleimageview.CircleImageView xmlns:app="http://schemas.android.com/apk/res-auto"
            android:id="@+id/profile_image"
            android:layout_width="44dp"
            android:layout_height="55dp"
            android:src="@drawable/profile"
            app:civ_border_color="@color/secondary_text"
            app:civ_border_width="2dp" />
        <TextView
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:text="Title"
            android:gravity="center"
            style="@style/Base.TextAppearance.AppCompat.Widget.ActionBar.Title"
            />


    </android.support.v7.widget.Toolbar>

我完全不明白你的問題 .. 但我找到了這樣的解決方案

要在 Toolbar 中使用自定義標題,您需要做的就是記住 Toolbar 只是一個奇特的 ViewGroup,因此您可以像這樣添加自定義標題:

<android.support.v7.widget.Toolbar
    android:id="@+id/toolbar_top"
    android:layout_height="wrap_content"
    android:layout_width="match_parent"
    android:minHeight="?attr/actionBarSize"
    android:background="@color/action_bar_bkgnd"
    app:theme="@style/ToolBarTheme" >
     <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Toolbar Title"
        android:layout_gravity="center"
        android:id="@+id/toolbar_title" />
</android.support.v7.widget.Toolbar>

這意味着您可以隨意設置 TextView 的樣式,因為它只是一個普通的 TextView。 因此,在您的活動中,您可以像這樣訪問標題:

Toolbar toolbarTop = (Toolbar) findViewById(R.id.toolbar_top);
TextView mTitle = (TextView) toolbarTop.findViewById(R.id.toolbar_title);
public void centerTitleAndSubtitle(Toolbar toolbar){
    // Save current title and subtitle
    final CharSequence originalTitle = toolbar.getTitle();
    final CharSequence originalSubtitle = toolbar.getSubtitle();

    // Temporarily modify title and subtitle to help detecting each
    toolbar.setTitle("title");
    toolbar.setSubtitle("subtitle");

    for(int i = 0; i < toolbar.getChildCount(); i++){
        View view = toolbar.getChildAt(i);

        if(view instanceof TextView){
            TextView textView = (TextView) view;


            if(textView.getText().equals("title")){
                // Customize title's TextView
                Toolbar.LayoutParams params = new Toolbar.LayoutParams(Toolbar.LayoutParams.WRAP_CONTENT, Toolbar.LayoutParams.MATCH_PARENT);
                params.gravity = Gravity.CENTER_HORIZONTAL;
                textView.setLayoutParams(params);

            } else if(textView.getText().equals("subtitle")){
                // Customize subtitle's TextView
                Toolbar.LayoutParams params = new Toolbar.LayoutParams(Toolbar.LayoutParams.WRAP_CONTENT, Toolbar.LayoutParams.MATCH_PARENT);
                params.gravity = Gravity.CENTER_HORIZONTAL;
                textView.setLayoutParams(params);
            }
        }

        // Restore title and subtitle
        toolbar.setTitle(originalTitle);
        toolbar.setSubtitle(originalSubtitle);
    }
}

如果您還想要自定義字體,請在此處查看我的其他答案: https : //stackoverflow.com/a/35723158/445548

在工具欄內使用自定義標題(帶重心)

     <android.support.v7.widget.Toolbar           
         android:layout_width="match_parent"
         android:layout_height="?attr/actionBarSize"
         android:animateLayoutChanges="true"
         android:backgroundTint="@color/colorPrimary"
         android:background="?attr/colorPrimary"
         android:elevation="4dp"
         android:minHeight="?android:attr/actionBarSize"
         app:layout_collapseMode="pin"
         app:layout_scrollFlags="scroll|exitUntilCollapsed"
         app:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar"
         app:popupTheme="@style/AppTheme.PopupOverlay"
         app:titleTextAppearance="@style/Toolbar.TitleText" >

      <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:id="@+id/toolbar_title"
            android:text="Title"
            android:layout_gravity="center"/>

     </android.support.v7.widget.Toolbar>

最好的解決方案是在ToolBar使用嵌套的TextView ,然后將layout_widthlayout_height設置為wrap_content 然后將layout_gravity設置為center 這樣它就不會被toolbar其他圖標所抵消。

這完成了我的工作!

Toolbar toolbar = findViewById(R.id.mytoolbar);
        TextView titleText = getProperties(new TextView(this));
        FrameLayout frameLayout = new FrameLayout(this);
        frameLayout.setLayoutParams(new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,ViewGroup.LayoutParams.MATCH_PARENT));
        frameLayout.addView(titleText);
        toolbar.addView(frameLayout);
        setSupportActionBar(toolbar);

設置 TextView 屬性的方法

 private TextView getProperties(TextView titleText){
        titleText.setText(wallpaperName);
        titleText.setTextColor(Color.WHITE);
        titleText.setTextSize(18f);
        titleText.setShadowLayer(2f,2f,2f,Color.BLACK);
        titleText.setTextAlignment(View.TEXT_ALIGNMENT_CENTER); // CENTER ALIGNMENT
        return titleText;
    }

在 koltin 中只有一項功能可以幫助您...

    private fun centerTitle(toolbar: Toolbar) {
    // Save current title
    val originalTitle: CharSequence = toolbar.title
    // Temporarily modify title
    toolbar.title = "title"
    for (i in 0 until toolbar.childCount) {
        val view: View = toolbar.getChildAt(i)
        if (view is TextView) {
            if (view.text == "title") {
                // Customize title's TextView
                val params: Toolbar.LayoutParams = Toolbar.LayoutParams(
                    Toolbar.LayoutParams.WRAP_CONTENT,
                    Toolbar.LayoutParams.MATCH_PARENT
                )
                params.gravity = Gravity.CENTER_HORIZONTAL
                view.layoutParams = params
            }
        }
        // Restore title
        toolbar.title = originalTitle
    }
}

來自@user2137020 的 kotlin 用戶回答:

package com.example.safetyofficer.view

import android.content.Context
import android.util.AttributeSet
import android.widget.TextView
import androidx.appcompat.widget.Toolbar
import com.example.safetyofficer.R


class CustomToolbar @JvmOverloads constructor(
    context: Context,
    attrs: AttributeSet? = null,
    defStyleAttr: Int = R.attr.toolbarStyle
) :
    Toolbar(context, attrs, defStyleAttr) {
    private val titleView: TextView = TextView(getContext())

    override fun onLayout(changed: Boolean, l: Int, t: Int, r: Int, b: Int) {
        super.onLayout(changed, l, t, r, b)
        titleView.x = (width - titleView.width) / 2.toFloat()
    }

    override fun setTitle(title: CharSequence) {
        titleView.text = title
    }

    init {
        val textAppearanceStyleResId: Int
        val a = context.theme.obtainStyledAttributes(
            attrs,
            intArrayOf(R.attr.titleTextAppearance),
            defStyleAttr,
            0
        )
        textAppearanceStyleResId = try {
            a.getResourceId(0, 0)
        } finally {
            a.recycle()
        }
        if (textAppearanceStyleResId > 0) {
            titleView.setTextAppearance(textAppearanceStyleResId)
        }
        addView(titleView, LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT))
    }
}

您可以使用 MaterialToolbar 並在 xml 中設置 app:titleCentered="true"。

我第一次在項目中使用ToolBar,所以我不知道如何在android中自定義工具欄。 我需要將標題居中放置在工具欄上,如何操作請告訴我。

預先感謝。

您可以將此代碼插入到您的代碼中

SupportActionBar.Title = "title";

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM