Заголовок центра панели инструментов Android и настраиваемый шрифт

Я пытаюсь найти правильный способ использовать собственный шрифт для заголовка панели инструментов и центрировать его на панели инструментов (требование клиента).

На данный момент я использую старый добрый ActionBar, и я устанавливал для заголовка пустое значение и использовал setCustomView, чтобы поместить свой собственный шрифт TextView и центрировать его с помощью ActionBar.LayoutParams.

Есть ли лучший способ сделать это? Использование новой панели инструментов в качестве панели действий.


person Mathbl    schedule 23.10.2014    source источник


Ответы (34)


Чтобы использовать настраиваемый заголовок в 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="?android: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);
person MrEngineer13    schedule 24.10.2014
comment
Предлагаем вместо этого использовать android: layout_width = wrap_content android: layout_height = wrap_content android: layout_gravity = center. - person SteelBytes; 06.11.2014
comment
Иногда android: layout_gravity = top помогает мне выровнять заголовок TextView со стрелкой ‹- панели инструментов. - person goRGon; 09.02.2015
comment
Этот метод у меня не сработал. Заголовок уже установлен как имя приложения. - person Doronz; 26.02.2015
comment
Вы можете очистить текст заголовка программно с помощью toolbarTop.setTitle (null) или удалить метку из своего манифеста. - person MrEngineer13; 26.02.2015
comment
Это также не сработало для меня .. появляется имя приложения, и я удалил метку действия в манифесте - person porthfind; 06.03.2015
comment
Если кто-то еще не может удалить заголовок имени приложения по умолчанию, сделайте следующее: 1. Вызовите setSupportActionBar (yourToolbar) 2. Вызовите getSupportActionBar (). SetDisplayShowTitleEnabled (false); - person Rick Sanchez; 17.03.2015
comment
Чтобы продолжать использовать стили по умолчанию для настраиваемого TextView, попробуйте что-нибудь вроде style="@style/TextAppearance.AppCompat.Widget.ActionBar.Title" (см. Этот ответ). - person Jonik; 25.03.2015
comment
вы отвечаете так здорово, НО, android: paddingTop = @ dimen / tool_bar_top_padding никогда не центрирует текст, потому что точка центра строки смещена. - person ; 27.07.2015
comment
Использование текстового представления внутри панели инструментов вызывает проблемы с виджетом поиска на панели инструментов. Если я использую виджет поиска на панели инструментов, при щелчке значка поиска он увеличивает высоту панели инструментов до примерно половины высоты экрана, но когда я удаляю это текстовое представление с панели инструментов, он начинает работать правильно. Любая идея? - person Ankur Chaudhary; 09.12.2015
comment
@ MrEngineer13 Я не могу применить это для CollapsingToobarLayout. Какие-либо предложения??? - person GreenROBO; 11.02.2016
comment
У меня ничего из этого не сработало. Возможно, потому, что моя панель инструментов включает меню, из-за которого Android отказывается от макета TextView для заголовка. - person AndroidDev; 12.05.2016
comment
Вы также можете удалить заголовок имени приложения по умолчанию, используя пустой android:label в объявлении AndroidManifest. - person saiyancoder; 20.07.2016
comment
добавление android: paddingRight =? attr / actionBarSize может помочь центрировать текст в середине экрана, если у вас есть кнопка (главная страница, панель навигации и т. д.) - person Gordak; 16.11.2016
comment
Проголосовали против этого год назад, потому что использовать стили проще. Но если вам нужен собственный шрифт, это лучший способ. Просто сделал то же самое. Тем не менее, вам потребуется немного больше настроек, чтобы убедиться, что заголовок вашего действия установлен в правильном представлении. - person DariusL; 30.11.2016
comment
Что произойдет, если на Панели инструментов появится значок Гамбургер? Он будет не в центре всей ширины панели инструментов, а в центре ToolbarWidth - HamburgerIconWidth. - person Akshay; 02.12.2016
comment
Единственный способ получить собственный шрифт, насколько я смог попробовать. - person Meanman; 14.02.2017
comment
Этот ответ не является хорошей идеей, потому что вы не можете использовать его в scrolling activity, когда вы прокручиваете вниз, пользовательский Textview будет скрыт, и будет показан исходный заголовок! Вы можете это проверить! это ответ очень запутанный. - person hossein masomzadeh; 05.03.2017
comment
для меня layout_gravity не работает на панели инструментов. он не отображается при автозаполнении, и когда я вручную набираю его, он ничего не делает. - person Siavash; 24.03.2017
comment
Почему это принятый ответ, если он явно не работает? - person breakline; 22.03.2018
comment
@Akshay попробуйте переместить TextView в FrameLayout обертку на панели инструментов - person R4j; 31.08.2018
comment
Мне пришлось использовать androidx.appcompat.widget.Toolbar, чтобы иметь возможность разместить Textview внутри панели инструментов - person Carson Holzheimer; 04.01.2019
comment
При таком подходе я получаю предупреждение requestLayout() improperly called by com.google.android.material.textview...during layout: running second layout pass - person MobDev; 27.05.2020

Это просто помогает объединить все части с помощью ответа @ MrEngineer13 с комментариями @Jonik и @Rick Sanchez в правильном порядке, чтобы помочь легко получить заголовок по центру !!

Макет с TextAppearance.AppCompat.Widget.ActionBar.Title:

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

        <TextView
            android:id="@+id/toolbar_title"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"                      
            style="@style/TextAppearance.AppCompat.Widget.ActionBar.Title"
            android:layout_gravity="center" />

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

Способ достижения с правильным порядком:

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    TextView mTitle = (TextView) toolbar.findViewById(R.id.toolbar_title);

    setSupportActionBar(toolbar);
    mTitle.setText(toolbar.getTitle());

    getSupportActionBar().setDisplayShowTitleEnabled(false);

Не забудьте проголосовать за ответ @ MrEngineer13 !!!

Вот пример проекта ToolbarCenterTitleSample

введите описание изображения здесь

Надеюсь помочь кому-то другому;)

person Gueorgui Obregon    schedule 04.07.2016
comment
если я установил setDisplayHomeAsUpEnabled (true) и setDisplayShowHomeEnabled (true); энальбе назад стрелка. Тогда титул не идет по центру. Я пробовал установить actionBar.setTitle (); и setDisplayShowTitleEnabled (ложь). Но все еще не смог решить проблему - person Prashanth Debbadwar; 18.11.2016
comment
Вы проверяли его на Scrolling Activity? - person hossein masomzadeh; 05.03.2017
comment
Верно, что со стрелкой назад заголовок не центрируется (он смещен вправо на половину ширины стрелки назад). Полагаю, если бы я был действительно настроен, я бы программно добавил достаточно поля справа от текстового поля по мере необходимости, чтобы центрировать текст. - person Someone Somewhere; 03.04.2018

Заголовок ToolBar стилизован. Любые изменения, которые вы делаете, должны выполняться в теме. Приведу вам пример.

Макет панели инструментов:

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.Toolbar
    style="@style/ToolBarStyle.Event"
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/toolbar"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="?attr/colorPrimary"
    android:minHeight="@dimen/abc_action_bar_default_height_material" />

Стили:

<style name="ToolBarStyle" parent="ToolBarStyle.Base"/>

<style name="ToolBarStyle.Base" parent="">
    <item name="popupTheme">@style/ThemeOverlay.AppCompat.Light</item>
    <item name="theme">@style/ThemeOverlay.AppCompat.Dark.ActionBar</item>
</style>

<style name="ToolBarStyle.Event" parent="ToolBarStyle">
    <item name="titleTextAppearance">@style/TextAppearance.Widget.Event.Toolbar.Title</item>
</style>

<style name="TextAppearance.Widget.Event.Toolbar.Title" parent="TextAppearance.Widget.AppCompat.Toolbar.Title">
    <!--Any text styling can be done here-->
    <item name="android:textStyle">normal</item>
    <item name="android:textSize">@dimen/event_title_text_size</item>
</style>
person Binoy Babu    schedule 17.02.2015
comment
Это правильный путь. Добавление еще одного TextView - это немного хакерство, но ответ отражения - просто зло. - person DariusL; 24.07.2015
comment
Чисто, но вы не можете установить собственный шрифт из стиля. Грустно. - person niqueco; 08.08.2015
comment
Вы также не можете изменить выравнивание заголовка. - person Terry; 10.08.2015
comment
@Terry Полагаю, это потому, что Google хочет, чтобы вы придерживались рекомендаций по дизайну. Лично я ненавижу, когда какое-то приложение пытается сделать ToolBar / ActionBar необычным. - person Binoy Babu; 10.08.2015
comment
@ user1560102 нет ничего хитрого в добавлении TextView на панель инструментов. Вот для чего он был разработан. - person Tim Malseed; 06.11.2015
comment
Это не центрирует текст. - person Sebastian Roth; 20.03.2016
comment
Не центрирует текст, как просил OP. - person david; 09.10.2017
comment
@niqueco: вы можете изменить шрифт с помощью <item name="android:fontFamily">@font/your_font_here</item> - person Frank; 23.01.2018
comment
Я следил за вашим кодом стиля, шрифт работал, но я не нашел способа выровнять текст по центру. Я пробовал это: ‹имя элемента = android: textAlignment› center ‹/item› ‹имя элемента = android: layout_centerHorizontal› true ‹/item› ‹имя элемента = android: gravity› center ‹/item› - person Kirk_hehe; 24.07.2019
comment
не смог центрировать текст, используя styles.xml. Я не думаю, что можно изменить выравнивание текста с помощью стилей. - person Anubhav; 06.11.2019

у нас нет прямого доступа к заголовку TextView панели инструментов, поэтому мы используем отражение для доступа к нему.

  private TextView getActionBarTextView() {
    TextView titleTextView = null;

    try {
        Field f = mToolBar.getClass().getDeclaredField("mTitleTextView");
        f.setAccessible(true);
        titleTextView = (TextView) f.get(mToolBar);
    } catch (NoSuchFieldException e) {
    } catch (IllegalAccessException e) {
    }
    return titleTextView;
}
person BugsBunnyBR    schedule 12.11.2014
comment
Хотя это хакерство, это решение работает для меня после попытки найти способ получить доступ к текстовому представлению панели инструментов. Спасибо. - person falc0nit3; 15.12.2014
comment
Это только при использовании настраиваемой панели инструментов вместо предоставленной? Иначе как получить доступ к объекту Toolbar (здесь mToolbar)? - person matiash; 23.12.2014
comment
Жаль, что в руководствах по материальному дизайну заголовок имеет отступы, но их нет по умолчанию, и у нас даже нет доступа к mTitleView. Благодарю за ответ. - person Oknesif; 06.02.2015
comment
Хорошо поработал для Заголовка. Но при попытке получить mSubtitleTextView таким образом возникла исключительная ситуация. Вызвано: java.lang.NullPointerException: попытка вызвать виртуальный метод void android.widget.TextView.setTypeface (android.graphics.Typeface) для ссылки на нулевой объект - person Vinod; 16.02.2015
comment
для субтитров следует использовать mSubtitleText, а не mSubtitleTextView - person BugsBunnyBR; 19.03.2015
comment
если вы хотите использовать getActionBarTextView (). setGravity (Gravity.CENTER) этот метод или в метод textview, java.lang.NullPointerException: попытка вызвать виртуальный метод void android.widget.TextView.setGravity (int) для нулевого объекта ссылка - person ; 27.07.2015
comment
Примечание. Вы можете получить доступ к полю mTitleTextView только после того, как зададите заголовок панели инструментов! Поле лениво инициализируется при первом использовании. - person funcoder; 10.08.2015
comment
Это решение спасло мне день и работает также с Xamarin. - person Daniele D.; 30.09.2015
comment
Что, если вы запутаете свой код с помощью ProGuard, и mTitleTextView станет abcde12345? - person voghDev; 27.10.2016
comment
@voghDev getDeclaredField в этом случае вызовет исключение NoSuchFieldException, в результате чего код не будет работать. - person Jeremy; 19.12.2016
comment
@voghDev поместите mTitleTextView в strings.xml и используйте его в коде. - person Vinay; 23.03.2018

Определите следующий класс:

public class CenteredToolbar extends Toolbar {

    private TextView centeredTitleTextView;

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

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

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

    @Override
    public void setTitle(@StringRes int resId) {
        String s = getResources().getString(resId);
        setTitle(s);
    }

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

    @Override
    public CharSequence getTitle() {
        return getCenteredTitleTextView().getText().toString();
    }

    public void setTypeface(Typeface font) {
        getCenteredTitleTextView().setTypeface(font);
    }

    private TextView getCenteredTitleTextView() {
        if (centeredTitleTextView == null) {
            centeredTitleTextView = new TextView(getContext());
            centeredTitleTextView.setTypeface(...);
            centeredTitleTextView.setSingleLine();
            centeredTitleTextView.setEllipsize(TextUtils.TruncateAt.END);
            centeredTitleTextView.setGravity(Gravity.CENTER);
            centeredTitleTextView.setTextAppearance(getContext(), R.style.TextAppearance_AppCompat_Widget_ActionBar_Title);

            Toolbar.LayoutParams lp = new Toolbar.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
            lp.gravity = Gravity.CENTER;
            centeredTitleTextView.setLayoutParams(lp);

            addView(centeredTitleTextView);
        }
        return centeredTitleTextView;
    }
}

... а затем просто используйте его вместо обычного Toolbar вот так:

<RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="@color/colorAccent">

        <your.packagename.here.CenteredToolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="?attr/colorPrimary"
            android:minHeight="?attr/actionBarSize"
            android:theme="?attr/actionBarTheme"
            app:title="@string/reset_password_page_title"/>

        <!-- Other views -->

</RelativeLayout>

Вам по-прежнему нужны эти 2 строки кода в вашем Activity (как и в стандартном Toolbar):

Toolbar toolbar = (Toolbar) findViewByid(R.id.toolbar); // note that your activity doesn't need to know that it is actually a custom Toolbar
setSupportActionBar(binding.toolbar);

Вот и все! Вам не нужно скрывать стандартный заголовок с выравниванием по левому краю, не нужно многократно дублировать один и тот же XML-код и т. Д., Просто используйте CenteredToolbar, как если бы он был по умолчанию Toolbar. Вы также можете установить собственный шрифт программно, поскольку теперь у вас есть прямой доступ к TextView. Надеюсь это поможет.

person fraggjkee    schedule 04.09.2017
comment
Спасибо! Лучшее решение, только не забыть импортировать на панель инструментов виджет v7.widget - person David; 07.04.2018
comment
Я знаю, что он довольно старый, но ... как я могу изменить цвет текста? Я пробовал использовать XML с app: titleTextColor и в коде с centeredTitleTextView.setColor. Есть идеи, @fraggjkee? - person Genaro Alberto Cancino Herrera; 17.05.2018
comment
centeredTitleTextView.setTextColor(...) должно работать - person fraggjkee; 18.05.2018
comment
Разве это не должно быть LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT)? - person liminal; 10.03.2019
comment
привет, что связывает? - person famfamfam; 18.10.2020

Вот подход, зависящий от текста заголовка, чтобы найти экземпляр TextView из Toolbar.

  public static TextView getToolbarTitleView(ActionBarActivity activity, Toolbar toolbar){
    ActionBar actionBar = activity.getSupportActionBar();
    CharSequence actionbarTitle = null;
    if(actionBar != null)
        actionbarTitle = actionBar.getTitle();
    actionbarTitle = TextUtils.isEmpty(actionbarTitle) ? toolbar.getTitle() : actionbarTitle;
    if(TextUtils.isEmpty(actionbarTitle)) return null;
    // can't find if title not set
    for(int i= 0; i < toolbar.getChildCount(); i++){
        View v = toolbar.getChildAt(i);
        if(v != null && v instanceof TextView){
            TextView t = (TextView) v;
            CharSequence title = t.getText();
            if(!TextUtils.isEmpty(title) && actionbarTitle.equals(title) && t.getId() == View.NO_ID){
                //Toolbar does not assign id to views with layout params SYSTEM, hence getId() == View.NO_ID
                //in same manner subtitle TextView can be obtained.
                return t;
            }
        }
    }
    return null;
}
person Nikola Despotoski    schedule 23.01.2015

Никто об этом не упомянул, но есть некоторые атрибуты для Toolbar:

app:titleTextColor для настройки цвета текста заголовка

app:titleTextAppearance для настройки внешнего вида текста заголовка

app:titleMargin для установки маржи

Есть и другие поля с определенной стороной, такие как marginStart и т. Д.

person Ali Bdeir    schedule 01.12.2016
comment
Идеальное решение .. если вам известно о FontOverride, просто создайте стиль в styles.xml <style name="customFontTextAppearanceStyle"> <item name="android:textSize">18sp</item> <item name="android:typeface">monospace</item> и примените его на панели инструментов app:titleTextAppearance="@styles/customFontTextAppearanceStyle" - person Chinmay Thoriya; 03.03.2017
comment
Я использовал этот метод, но с моей панелью инструментов ничего не случилось! я создал новый «‹style›» и установил для него значение app:titleTextAppearanc="style name" на android.support.v7.widget.Toolbar ТЕГЕ - person hossein masomzadeh; 05.03.2017

Я использую это решение:

static void centerToolbarTitle(@NonNull final Toolbar toolbar) {
    final CharSequence title = toolbar.getTitle();
    final ArrayList<View> outViews = new ArrayList<>(1);
    toolbar.findViewsWithText(outViews, title, View.FIND_VIEWS_WITH_TEXT);
    if (!outViews.isEmpty()) {
        final TextView titleView = (TextView) outViews.get(0);
        titleView.setGravity(Gravity.CENTER);
        final Toolbar.LayoutParams layoutParams = (Toolbar.LayoutParams) titleView.getLayoutParams();
        layoutParams.width = ViewGroup.LayoutParams.MATCH_PARENT;
        toolbar.requestLayout();
        //also you can use titleView for changing font: titleView.setTypeface(Typeface);
    }
}
person ultraon    schedule 05.01.2016
comment
Работает очень хорошо, но по какой-то причине не центрируется должным образом с панелями инструментов, на которых нет кнопки элемента. - person Munib; 28.08.2017
comment
Дополнение: если у вас есть значок навигации или назад на панели инструментов, заголовок не остается точно по центру. Я добавляю пустой значок меню настроек для этой ситуации. Мой пустой пункт меню: ‹item android: id = @ + id / empty android: orderInCategory = 100 android: icon = @ android: color / transparent app: showAsAction = always tools: ignore = MenuTitle /› - person Mete; 07.09.2018

Без панели инструментов TextView мы можем настроить шрифт, используя приведенный ниже код

getSupportActionBar().setDisplayShowTitleEnabled(false);
or
getActionBar().setDisplayShowTitleEnabled(false);

public void updateActionbar(String title){
    SpannableString spannableString = new SpannableString(title);
    spannableString.setSpan(new TypefaceSpanString(this,  "futurastdmedium.ttf"),
            0, spannableString.length(),
            Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
    mToolbar.setTitle(spannableString);
}
person Ajit Kumar Dubey    schedule 05.09.2015
comment
Если вам просто нужно изменить шрифт, это кажется наиболее чистым решением. ПРИМЕЧАНИЕ. TypefaceSpanString - это просто следующее: stackoverflow.com/a/17961854 - person Mohib Irshad; 26.12.2016

Макет:

<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="match_parent"
        android:layout_height="wrap_content"
        android:text="Toolbar Title"
        android:layout_gravity="center"
        android:gravity="center"
        android:id="@+id/toolbar_title" />
</android.support.v7.widget.Toolbar>

Код:

    Toolbar mToolbar = parent.findViewById(R.id.toolbar_top);
    TextView mToolbarCustomTitle = parent.findViewById(R.id.toolbar_title);

    //setup width of custom title to match in parent toolbar
    mToolbar.postDelayed(new Runnable()
    {
        @Override
        public void run ()
        {
            int maxWidth = mToolbar.getWidth();
            int titleWidth = mToolbarCustomTitle.getWidth();
            int iconWidth = maxWidth - titleWidth;

            if (iconWidth > 0)
            {
                //icons (drawer, menu) are on left and right side
                int width = maxWidth - iconWidth * 2;
                mToolbarCustomTitle.setMinimumWidth(width);
                mToolbarCustomTitle.getLayoutParams().width = width;
            }
        }
    }, 0);
person maros136    schedule 06.05.2015
comment
Думаю, int width = maxWidth - titleWidth * 2; должно быть int width = maxWidth - iconWidth * 2;, думает! - person oldfeel; 19.07.2015

Очень быстрый и простой способ установить собственный шрифт - использовать пользовательский titleTextAppearance с fontFamily:

Добавьте в styles.xml:

<style name="ToolbarTitle" parent="TextAppearance.Widget.AppCompat.Toolbar.Title">
    <item name="android:textSize">16sp</item>
    <item name="android:textColor">#FF202230</item>
    <item name="android:fontFamily">@font/varela_round_regular</item>
</style>

В папке res создайте папку font (например, varela_round_regular.ttf)

Прочтите официальное руководство, чтобы узнать больше https://developer.android.com/guide/topics/ui/look-and-feel/fonts-in-xml.html

person vovahost    schedule 22.01.2018

Я не знаю, изменилось ли что-нибудь в библиотеке appcompat, но это довольно тривиально, не нужно размышлять.

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

// loop through all toolbar children right after setting support 
// action bar because the text view has no id assigned

// also make sure that the activity has some title here
// because calling setText() with an empty string actually
// removes the text view from the toolbar

TextView toolbarTitle = null;
for (int i = 0; i < toolbar.getChildCount(); ++i) {
    View child = toolbar.getChildAt(i);

    // assuming that the title is the first instance of TextView
    // you can also check if the title string matches
    if (child instanceof TextView) {
        toolbarTitle = (TextView)child;
        break;
    }
}
person headsvk    schedule 05.10.2015

Решение, которое я использовал для этой проблемы:

 public static void applyFontForToolbarTitle(Activity a){
        Toolbar toolbar = (Toolbar) a.findViewById(R.id.app_bar);
        for(int i = 0; i < toolbar.getChildCount(); i++){
            View view = toolbar.getChildAt(i);
            if(view instanceof TextView){
                TextView tv = (TextView) view;
                if(tv.getText().equals(a.getTitle())){
                    tv.setTypeface(getRuneTypefaceBold(a));
                    break;
                }
            }
        }
    }

Я думаю, что для центра тяжести необходимо изменить параметры макета на match_parent по горизонтали, а затем:

tv.setGravity(Gravity.CENTER);
person Monet_z_Polski    schedule 31.10.2015

Я решил это решение, и это следующие коды:

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

        <TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:text="Order History"
            android:layout_gravity="center"
            android:id="@+id/toolbar_title"
            android:textSize="17sp"
            android:textStyle="bold"
            android:textColor="@color/colorWhite"
            />

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

И вы можете изменить заголовок / метку, в Activity напишите следующие коды:

Toolbar toolbarTop = (Toolbar) findViewById(R.id.toolbar_top);

TextView mTitle = (TextView) toolbarTop.findViewById (R.id.toolbar_title); mTitle.setText ("@ строка / ....");

person Hai Rom    schedule 07.06.2016

Вы можете использовать следующее

 <android.support.v7.widget.Toolbar
    android:id="@+id/top_actionbar"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:theme="@style/AppThemeToolbar">

    <TextView
        android:id="@+id/pageTitle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        />
</android.support.v7.widget.Toolbar>
person A Sharma    schedule 21.10.2016
comment
если я установил setDisplayHomeAsUpEnabled (true) и setDisplayShowHomeEnabled (true); энальбе назад стрелка. Тогда титул не идет по центру. Я пробовал установить actionBar.setTitle (); и setDisplayShowTitleEnabled (ложь). Но все еще не смог решить проблему - person Prashanth Debbadwar; 18.11.2016

MaterialToolbar из Компоненты материала 1.4.0-alpha02 теперь имеет возможность центрировать заголовок панели инструментов, установив для атрибута titleCentered значение true:

<com.google.android.material.appbar.AppBarLayout
    android:id="@+id/appBarLayout"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">

    <com.google.android.material.appbar.MaterialToolbar
        android:id="@+id/topAppBar"
        style="@style/Widget.MaterialComponents.Toolbar.Primary"
        android:layout_width="match_parent"
        android:layout_height="?attr/actionBarSize"
        app:titleCentered="true" />

</com.google.android.material.appbar.AppBarLayout>
person user3210008    schedule 09.04.2021

Обновление из ответа @ MrEngineer13: чтобы выровнять центр заголовка в любых случаях, включая значок гамбургера, меню параметров, вы можете добавить FrameLayout на панели инструментов следующим образом:

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

         <FrameLayout android:layout_width="match_parent"
                    android:layout_height="match_parent">

              <TextView
               android:layout_width="wrap_content"
               android:layout_height="wrap_content"
               android:text="Toolbar Title"
               android:layout_gravity="center"
               style="@style/TextAppearance.AppCompat.Widget.ActionBar.Title"
               android:id="@+id/toolbar_title" />

        </FrameLayout>

   </android.support.v7.widget.Toolbar>
person R4j    schedule 31.08.2018

Несмотря на то, что добавление текстового представления на панель инструментов может решить проблему ограничения стиля заголовка, с этим есть проблема. Поскольку мы не добавляем его в макет, у нас нет особого контроля над его шириной. Мы можем использовать либо wrap_content, либо match_parent.

Теперь рассмотрим сценарий, в котором у нас есть searchView в виде кнопки на правом краю панели инструментов. Если содержание заголовка больше, оно будет поверх кнопки, скрывая его. Невозможно управлять этим, кроме установки ширины метки, и это то, чего вы не хотите делать, если хотите иметь адаптивный дизайн.

Итак, вот решение, которое сработало для меня, которое немного отличается от добавления текстового представления на панель инструментов. Вместо этого добавьте панель инструментов и текстовое представление в относительный макет и убедитесь, что текстовое представление находится наверху панели инструментов. Затем мы можем использовать соответствующие поля и убедиться, что текстовое представление отображается там, где мы хотим, чтобы оно отображалось.

Убедитесь, что на панели инструментов не отображается заголовок.

Вот XML для этого решения:

<RelativeLayout
                    android:orientation="horizontal"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:background="?attr/colorPrimary">

                    <android.support.v7.widget.Toolbar
                        android:theme="@style/ThemeOverlay.AppCompat.Dark"
                        android:id="@+id/activity_toolbar"
                        android:layout_width="match_parent"
                        android:layout_height="?attr/actionBarSize"
                        android:background="?attr/colorPrimary"
                        android:titleTextAppearance="@style/AppTheme.TitleTextView"
                        android:layout_marginRight="40dp"
                        android:layoutMode="clipBounds">

                        <android.support.v7.widget.SearchView
                            android:id="@+id/search_view"
                            android:layout_width="wrap_content"
                            android:layout_height="wrap_content"
                            android:layout_gravity="right"
                            android:layout_centerVertical="true"
                            android:layout_alignParentRight="true"
                            android:foregroundTint="@color/white" />
                        </android.support.v7.widget.Toolbar>

                    <TextView
                        android:id="@+id/toolbar_title"
                        android:layout_width="match_parent"
                        android:layout_height="wrap_content"
                        android:layout_marginRight="90dp"
                        android:text="@string/app_name"
                        android:textSize="@dimen/title_text_size"
                        android:textColor="@color/white"
                        android:lines="1"
                        android:layout_marginLeft="72dp"
                        android:layout_centerVertical="true" />

                </RelativeLayout>

Решает проблему @ ankur-chaudhary, упомянутую выше.

person Deepak G M    schedule 26.02.2016

Поскольку android.support.v7.appcompat 24.2 Toolbar имеет метод setTitleTextAppearance, и вы можете установить его шрифт без внешнего textview.

создать новый стиль в styles.xml

<style name="RobotoBoldTextAppearance">
        <item name="android:fontFamily">@font/roboto_condensed_bold</item>
</style>

и использовать это

mToolbar.setTitleTextAppearance(this, R.style.RobotoBoldTextAppearance);
person Rainmaker    schedule 26.08.2017

Несколько дней я искал универсальное решение. Моя панель инструментов работает с меню Android и значком навигации.

Сначала вам нужно создать собственный класс панели инструментов. Этот класс должен иметь вычисление позиций по центру заголовка (отступов):

    class CenteredToolbar @JvmOverloads constructor(context: Context, attrs: AttributeSet? = null, defStyleAttr: Int = 0)
    : Toolbar(context, attrs, defStyleAttr) {

    init {
        addOnLayoutChangeListener(object : View.OnLayoutChangeListener {
            override fun onLayoutChange(v: View?, left: Int, top: Int, right: Int, bottom: Int, oldLeft: Int, oldTop: Int, oldRight: Int, oldBottom: Int) {
                val titleTextView = findViewById<TextView>(R.id.centerTitle)

                val x = titleTextView.x.toInt()
                val x2 = x + titleTextView.width

                val fullWidth = width
                val fullCenter = fullWidth / 2

                val offsetLeft = Math.abs(fullCenter - x)
                val offsetRight = Math.abs(x2 - fullCenter)
                val differOffset = Math.abs(offsetLeft - offsetRight)

                if (offsetLeft > offsetRight) {
                    titleTextView.setPadding(differOffset, 0, 0, 0)
                } else if (offsetRight > offsetLeft) {
                    titleTextView.setPadding(0, 0, differOffset, 0)
                }

                removeOnLayoutChangeListener(this)
            }
        })
    }

    override fun setTitle(resId: Int) = getTitleView().setText(resId)

    override fun setTitle(title: CharSequence?) = getTitleView().setText(title)

    fun getTitleView(): TextView = findViewById(R.id.centerTitle)

}

Во-вторых, вам нужно создать панель инструментов макета:

<CenteredToolbar xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/toolbar">

    <TextView
        android:id="@+id/centerTitle"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"/>

</CenteredToolbar>

Это все

person Valery Boretsky    schedule 12.08.2018

Попробуйте выделить панель инструментов и титр в отдельном окне. Взгляните на правый конец и дайте им вес, равный весу панели инструментов. Таким образом, ваш титул окажется в центре.

<android.support.design.widget.AppBarLayout
    android:id="@+id/app_bar"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:theme="@style/AppTheme.AppBarOverlay"
    android:background="@color/white_color">
  <LinearLayout
   android:id="@+id/toolbar_layout"
   android:layout_width="match_parent"
   android:layout_height="wrap_content"
   android:background="@color/white_color">

    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_width="0dp"
        android:layout_height="?attr/actionBarSize"
        android:background="@color/white_color"
        app:popupTheme="@style/AppTheme.PopupOverlay"
        app:contentInsetLeft="0dp"
        app:contentInsetStart="0dp"
        android:layout_weight="0.2"

        app:contentInsetStartWithNavigation="0dp"
        app:navigationIcon="@color/greyTextColor">
       </android.support.v7.widget.Toolbar>


        <com.an.customfontview.CustomTextView
            android:id="@+id/headingText"
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="0.6"
            android:gravity="center"
            android:text="Heading"
            android:layout_centerHorizontal="true"
            android:layout_centerVertical="true"
            android:textColor="@color/colorPrimary"
            android:textSize="@dimen/keyboard_number"
            android:layout_gravity="center_horizontal|center_vertical"
            app:textFontPath="fonts/regular.ttf" />
            <ImageView
                android:id="@+id/search_icon"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_alignParentEnd="true"
                android:layout_centerVertical="true"
                android:visibility="visible"
                android:layout_weight="0.2"
                android:layout_gravity="center_horizontal|center_vertical"
                android:src="@drawable/portfolio_icon"/>
        </LinearLayout>

       </android.support.design.widget.AppBarLayout>
person Diya Bhat    schedule 15.04.2019

Вы можете вставить этот код в свой xml файл

 <androidx.appcompat.widget.Toolbar xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="@color/colorPrimaryDark"
    android:elevation="4dp"
    android:theme="@style/ThemeOverlay.AppCompat.ActionBar">

    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="Toolbar Title"
        android:textColor="#000000"
        android:textSize="20dp"
        android:id="@+id/toolbar_title" />

</androidx.appcompat.widget.Toolbar>
person Uzair Ahmed    schedule 17.09.2019
comment
Привет Узаир. Какой файл xml? Я использую проект Android Studio 3.6.3, созданный из шаблона пустого действия. Спасибо. - person Love and peace - Joe Codeswell; 06.05.2020

Чтобы использовать настраиваемый заголовок на панели инструментов, вы можете добавить настраиваемый заголовок, например:

<?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-auto"
    android:id="@+id/toolbar"
    android:layout_width="match_parent"
    android:layout_height="?attr/actionBarSize"
    android:background="?attr/colorPrimary"
    android:elevation="5dp"
    app:contentInsetLeft="0dp"
    app:contentInsetStart="0dp"
    app:popupTheme="@style/ThemeOverlay.AppCompat.Light"
    app:theme="@style/ThemeOverlay.AppCompat.Dark">


        <LinearLayout
            android:id="@+id/lnrTitle"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:gravity="center_horizontal"
            android:orientation="vertical">

            <TextView
                android:id="@+id/txvHeader"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_gravity="center_horizontal|center"
                android:gravity="center"
                android:ellipsize="end"
                android:maxLines="1"
                android:text="Header"
                android:textColor="@color/white"
                android:textSize="18sp" />


        </LinearLayout>


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

Код Java:

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

setSupportActionBar(toolbar);

if (getSupportActionBar() == null)
    return;

getSupportActionBar().setTitle("Title");

getSupportActionBar().setDisplayHomeAsUpEnabled(true);

person Alok Singh    schedule 22.12.2018

для пользовательского шрифта на панели инструментов вы можете переопределить шрифт textView в стиле, а затем каждый textView в вашем приложении также автоматически изменил шрифт заголовка панели инструментов, я тестировал его в android studio 3.1.3

в стиле сделать это:

<style name="defaultTextViewStyle" parent="android:Widget.TextView">
        <item name="android:fontFamily">@font/your_custom_font</item>
</style>

а затем в своей теме используйте это:

<item name="android:textViewStyle">@style/defaultTextViewStyle</item>
person Ali Khaki    schedule 06.10.2018

Я нашел другой способ добавить настраиваемую панель инструментов без какого-либо специального кода Java / Kotlin.

  • Во-первых: создайте XML с вашим настраиваемым макетом панели инструментов с AppBarLayout в качестве родителя:

    <?xml version="1.0" encoding="utf-8"?>
    <android.support.design.widget.AppBarLayout                     
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:theme="@style/AppTheme.AppBarOverlay">
    
    <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">
    
        <ImageView
            android:layout_width="80dp"
            android:layout_height="wrap_content"
            android:layout_gravity="right"
            android:layout_marginEnd="@dimen/magin_default"
            android:src="@drawable/logo" />
    
    </android.support.v7.widget.Toolbar>
    

  • Second: Include the toolbar in your layout:

    <?xml version="1.0" encoding="utf-8"?>                
    <android.support.constraint.ConstraintLayout 
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="@color/blue"
        tools:context=".app.MainAcitivity"
        tools:layout_editor_absoluteY="81dp">
    
        <include
            layout="@layout/toolbar_inicio"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toTopOf="parent" />
    
        <!-- Put your layout here -->
    
    </android.support.constraint.ConstraintLayout>
    
person Ângelo Polotto    schedule 09.11.2018

На мой взгляд, у вас есть два варианта:

1) Отредактируйте XML панели инструментов. Когда ваша панель инструментов добавляется в XML, это обычно выглядит так:

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

если вы хотите настроить его, просто удалите '/' в конце и сделайте так:

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

            <android.support.constraint.ConstraintLayout
                android:layout_width="match_parent"
                android:layout_height="match_parent">

                <ImageView
                    android:id="@+id/toolbar_iv"
                    android:layout_width="30dp"
                    android:layout_height="30dp"
                    android:src="@mipmap/ic_launcher"
                    app:layout_constraintBottom_toBottomOf="parent"
                    app:layout_constraintLeft_toLeftOf="parent"
                    app:layout_constraintTop_toTopOf="parent" />

                <TextView
                    android:id="@+id/toolbar_tv"
                    android:layout_width="wrap_content"
                    android:layout_height="match_parent"
                    android:layout_marginLeft="20dp"
                    android:gravity="center"
                    app:layout_constraintBottom_toBottomOf="parent"
                    app:layout_constraintLeft_toRightOf="@+id/toolbar_iv"
                    app:layout_constraintTop_toTopOf="parent" />

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

таким образом вы можете иметь панель инструментов и настраивать текстовое представление и логотип.

2) Программно измените собственное текстовое представление и значок:

Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
getSupportActionBar().setIcon(R.drawable.ic_question_mark);
getSupportActionBar().setTitle("Title");

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

person Idan Damri    schedule 25.12.2018

Вы можете настроить TextView на панели инструментов следующим образом:

<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="Title"
        android:layout_gravity="center"
        android:id="@+id/toolbar_title" />


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

Итак, это центрирует текст. Если вы хотите добавить собственный шрифт к обычному Toolbar, сделайте <style>:

<style android:name="ToolbarFont">
    <item android:fontFamily = "@font/fontName" />
</style>

И добавляем на панель инструментов:

toolbar.setTitleTextAppearance(this, R.style.ToolbarFont);

Для текстового представления на панели инструментов вы можете определить его с помощью атрибута fontFamily:

<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="Title"
        android:layout_gravity="center"
        android:id="@+id/toolbar_title"
        android:fontFamily="@font/fontFamily" />


</android.support.v7.widget.Toolbar>
person Gourav    schedule 09.02.2019

Я столкнулся с той же проблемой, исправленной в MainActivity.

Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
TextView mTitle = (TextView) toolbar.findViewById(R.id.toolbar_title);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayShowTitleEnabled(false);

И во фрагменте

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    if (view == null) {
        // Inflate the layout for this fragment
        view = inflater.inflate(R.layout.fragment_example, container, false);
        init();
    }
    getActivity().setTitle("Choose Fragment");
    return view;
}

@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
    inflater.inflate(R.menu.example_menu, menu);
}
person VINAY DANARADDI    schedule 13.03.2019

Пытаться

@Override
    public void onBackPressed() {
          if(getTitle().equals(getResources().getString(R.string.app_name))) {
            super.onBackPressed();}
          else {
//set visiblity
           }
}
person Sỹ Phạm    schedule 11.03.2016

У меня сработала настройка android:gravity="center"

Никакого стайлинга. Панель инструментов - это, по сути, ViewGroup все, что вам нужно сделать, это установить на ней гравитацию элементов.

        <android.support.v7.widget.Toolbar
            android:id="@+id/htab_toolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            android:layout_gravity="top"
            android:background="@color/partial_transparent"
            android:gravity="center"
            app:layout_collapseMode="pin"
            app:layout_scrollFlags="scroll|enterAlways"
            app:popupTheme="@style/ThemeOverlay.AppCompat.Light" />
person Hitesh Sahu    schedule 26.05.2017
comment
Не работает с androidx.appcompat.widget.Toolbar - person tmm1; 26.10.2018

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

(toolbar[0] as AppCompatTextView).let {
            it.viewTreeObserver.addOnDrawListener {
                it.layoutParams = it.layoutParams.apply {
                    width = Toolbar.LayoutParams.MATCH_PARENT
                    (this as ViewGroup.MarginLayoutParams).apply {
                        marginEnd = toolbar[1].width
                    }
                }
                it.textAlignment = View.TEXT_ALIGNMENT_CENTER
            }

        }
person Waqar Afzal    schedule 09.02.2021

Вам нужно просто добавить следующую строку в макет панели инструментов:

app:contentInsetStart="0dp"
person Diya Bhat    schedule 10.04.2019
comment
Проверьте мой новый ответ. Надеюсь, это поможет. - person Diya Bhat; 15.04.2019

Typeface face= Typeface.createFromAsset(getAssets(), "font/font.ttf"); // your custom font
Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
toolbar.setTypeface(face);
setSupportActionBar(toolbar);

Другой учебник:

  1. Пример панели инструментов Android
  2. Использование пользовательского шрифта в Android
  3. Руководство по ActionBar с примером
person Half Moon    schedule 14.01.2016
comment
В классе android.support.v7.widget.Toolbar нет метода setTypeface. - person Ali Yucel Akgul; 06.05.2016

person    schedule
comment
решение отлично работает, когда вы выводите последние две строки кода, его не должно быть внутри цикла for: // Восстановить заголовок и субтитры toolbar.setTitle (originalTitle); toolbar.setSubtitle (исходный субтитр); - person Ivan Stojkovic; 04.01.2017