Раскраски кнопок в Android с помощью Material Design и AppCompat

256

До AppCompatсегодняшнего обновления я смог изменить цвет кнопок в Android L, но не в старых версиях. После включения нового обновления AppCompat я не могу изменить цвет для любой версии, когда я пытаюсь попробовать кнопка просто исчезает. Кто-нибудь знает, как изменить цвет кнопки?

На следующих рисунках показано, чего я хочу достичь:

изображение, показывающее желаемый результат

Белая кнопка по умолчанию, красная - то, что я хочу.

Это то, что я делал ранее, чтобы изменить цвет кнопок в styles.xml:

<item name="android:colorButtonNormal">insert color here</item>

и сделать это динамически:

button.getBackground().setColorFilter(getResources().getColor(insert color here), PorterDuff.Mode.MULTIPLY);

Также я изменил родителя темы с @android:style/Theme.Material.Light.DarkActionBarнаTheme.AppCompat.Light.DarkActionBar

mail929
источник
Я попробовал то же самое, но ничего не изменило цвет кнопки. Я также удалил android: из атрибута, потому что он из библиотеки поддержки и не является частью пространства имен android
Informatic0re
Если вы используете Android: colorButtonNormal с Android 5.0, он работает - но, похоже, не совместим с предыдущими версиями
Informatic0re
Да, это именно то, что я испытывал
mail929
Я также понял, что цвет акцента не меняет цвет CheckBox, но в старых версиях
Informatic0re
плюс один для этого динамического метода. :)
theapache64

Ответы:

222

Официально исправлено в Библиотеке поддержки ред.22 (пт 13 марта 2015 г.). См. Соответствующую проблему кода Google:

https://issuetracker.google.com/issues/37008632

Пример использования

theme.xml:

<item name="colorButtonNormal">@color/button_color</item>

v21 / theme.xml

<item name="android:colorButtonNormal">@color/button_color</item>
WindRider
источник
17
Есть ли пример, как его использовать? Как я могу установить цвета только на одну кнопку?
Интриги
3
@WindRider У меня проблема, хотя, я хочу использовать его для создания кнопок с разными цветами. Я создаю стили Button.Red, Button.Green, все с родителями равно базовому стилю кнопки. Я установил элемент colorButtonNormal для запрашиваемого цвета, установите это как тему кнопки. К сожалению, это только цвета кнопок для 21. Ниже он не переопределяет colorButtonNormal, определенный в теме.
dominik4142
71
С AppCompat 22.1.1 он работает для меня на 2.3.7, 4.4.4 и 5.1 тоже только для одной кнопки: настройка кнопок android:theme="@style/ColoredButton", а в styles.xml <style name="ColoredButton" parent="Widget.AppCompat.Button"> <item name="colorButtonNormal">@color/button_yellow</item> </style>
hunyadym
2
@hunyadym, по какой-то причине добавление темы к кнопкам прерывается на клике. Я бы классифицировал это как обходной путь, пока библиотека дизайна не предоставит лучший способ.
gladed
3
@gladed: в вашем случае проблема заключается в следующем баге: code.google.com/p/android/issues/detail?id=62795#c1
hunyadym
148

Изменить (22.06.2016):

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

Оригинальный ответ:

Поскольку этот AppCompat не поддерживает кнопку, вы можете использовать xml в качестве фона. Для этого я взглянул на исходный код Android и нашел соответствующие файлы для оформления кнопок материалов.

1 - Посмотрите на оригинальную реализацию материала кнопки из источника.

Взгляните на btn_default_material.xml в исходном коде Android .

Вы можете скопировать файл в папку вашего проекта drawable-v21. Но не трогай цвет здесь. Файл, который нужно изменить, является вторым файлом.

Drawable-V21 / custom_btn.xml

<ripple xmlns:android="http://schemas.android.com/apk/res/android"
    android:color="?attr/colorControlHighlight">
    <item android:drawable="@drawable/btn_default_mtrl_shape" />
</ripple>

2 - Получить форму оригинального материала кнопкой

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

<inset xmlns:android="http://schemas.android.com/apk/res/android"
   android:insetLeft="@dimen/button_inset_horizontal_material"
   android:insetTop="@dimen/button_inset_vertical_material"
   android:insetRight="@dimen/button_inset_horizontal_material"
   android:insetBottom="@dimen/button_inset_vertical_material">
<shape android:shape="rectangle">
    <corners android:radius="@dimen/control_corner_material" />
    <solid android:color="?attr/colorButtonNormal" />
    <padding android:left="@dimen/button_padding_horizontal_material"
             android:top="@dimen/button_padding_vertical_material"
             android:right="@dimen/button_padding_horizontal_material"
             android:bottom="@dimen/button_padding_vertical_material" />
</shape>

3 - Получение размеров кнопки материала

И в этом файле вы используете некоторые измерения из файла, который вы можете найти здесь . Вы можете скопировать весь файл и поместить в вашу папку значений . Это важно для применения одинакового размера (который используется в кнопках материала) ко всем кнопкам

4 - Создайте еще один нарисованный файл для старых версий

Для более старых версий у вас должен быть другой drawable с тем же именем. Я непосредственно помещаю пункты в линию вместо ссылки. Вы можете ссылаться на них. Но опять же, самое главное, это оригинальные размеры материала кнопки.

рисуем / custom_btn.xml

    <?xml version="1.0" encoding="utf-8"?>
    <selector xmlns:android="http://schemas.android.com/apk/res/android">
    
    <!-- pressed state -->
    <item android:state_pressed="true">
        <inset xmlns:android="http://schemas.android.com/apk/res/android"
            android:insetLeft="@dimen/button_inset_horizontal_material"
            android:insetTop="@dimen/button_inset_vertical_material"
            android:insetRight="@dimen/button_inset_horizontal_material"
            android:insetBottom="@dimen/button_inset_vertical_material">
            <shape android:shape="rectangle">
                <corners android:radius="@dimen/control_corner_material" />
                <solid android:color="@color/PRESSED_STATE_COLOR" />
                <padding android:left="@dimen/button_padding_horizontal_material"
                    android:top="@dimen/button_padding_vertical_material"
                    android:right="@dimen/button_padding_horizontal_material"
                    android:bottom="@dimen/button_padding_vertical_material" />
            </shape>
        </inset>
    </item>
    
    <!-- focused state -->
    <item android:state_focused="true">
        <inset xmlns:android="http://schemas.android.com/apk/res/android"
            android:insetLeft="@dimen/button_inset_horizontal_material"
            android:insetTop="@dimen/button_inset_vertical_material"
            android:insetRight="@dimen/button_inset_horizontal_material"
            android:insetBottom="@dimen/button_inset_vertical_material">
            <shape android:shape="rectangle">
                <corners android:radius="@dimen/control_corner_material" />
                <solid android:color="@color/FOCUSED_STATE_COLOR" />
                <padding android:left="@dimen/button_padding_horizontal_material"
                    android:top="@dimen/button_padding_vertical_material"
                    android:right="@dimen/button_padding_horizontal_material"
                    android:bottom="@dimen/button_padding_vertical_material" />
            </shape>
        </inset>
    </item>
    
    <!-- normal state -->
    <item>
        <inset xmlns:android="http://schemas.android.com/apk/res/android"
            android:insetLeft="@dimen/button_inset_horizontal_material"
            android:insetTop="@dimen/button_inset_vertical_material"
            android:insetRight="@dimen/button_inset_horizontal_material"
            android:insetBottom="@dimen/button_inset_vertical_material">
            <shape android:shape="rectangle">
                <corners android:radius="@dimen/control_corner_material" />
                <solid android:color="@color/NORMAL_STATE_COLOR" />
                <padding android:left="@dimen/button_padding_horizontal_material"
                    android:top="@dimen/button_padding_vertical_material"
                    android:right="@dimen/button_padding_horizontal_material"
                    android:bottom="@dimen/button_padding_vertical_material" />
            </shape>
        </inset>
    </item>
</selector>

результат

Ваша кнопка будет иметь волновой эффект на устройствах Lollipop. Старые версии будут иметь точно такую ​​же кнопку, кроме эффекта ряби. Но с тех пор, как вы предоставите рисованные элементы для разных состояний, они также будут реагировать на сенсорные события (как по старинке).

eluleci
источник
4
Да, точно. Если вы используете один и тот же фон для всех кнопок и не хотите добавлять его снова и снова, определите стиль кнопки в вашем styles.xml <style name = "ButtonStyle" parent = "android: Widget.Button"> < item name = "android: background"> ​​@ drawable / custom_btn </ item> </ style> и добавьте стиль кнопки в свою тему <item name = "android: buttonStyle"> @ style / ButtonStyle </ item>
eluleci
1
как я могу добавить высоту к этой кнопке до 21 года? как я понимаю, я должен добавить новую форму с тенью под кнопкой, но куда именно я должен ее поместить?
Xakz
7
Очень раздражает, что это не поддерживается из коробки
Сэм,
39
Я полностью согласен с тобой. Кнопка - это наиболее часто используемый виджет, но он не включен в библиотеку поддержки материалов. Интересно, что они думают.
eluleci
1
Кроме того, следуя вашему руководству, кажется, что фон вообще не появляется ...
JMRboosties
111

Это было улучшено в v23.0.0 библиотеки AppCompat с добавлением большего количества тем, включая

Widget.AppCompat.Button.Colored

Прежде всего, включите зависимость appCompat, если вы еще этого не сделали

compile('com.android.support:appcompat-v7:23.0.0') {
    exclude group: 'com.google.android', module: 'support-v4'
}

теперь, так как вам нужно использовать v23 приложения-компата, вам также нужно будет использовать SDK-v23!

    compileSdkVersion = 23
    targetSdkVersion = 23

В твоем values/theme

<item name="android:buttonStyle">@style/BrandButtonStyle</item>

В твоем values/style

<style name="BrandButtonStyle" parent="Widget.AppCompat.Button.Colored">
    <item name="colorButtonNormal">@color/yourButtonColor</item>
    <item name="android:textColor">@color/White</item>
</style>

В твоем values-v21/style

<style name="BrandButtonStyle" parent="Widget.AppCompat.Button.Colored">
    <item name="android:colorButtonNormal">@color/yourButtonColor</item>
    <item name="android:textColor">@color/White</item>
</style>

Поскольку тема вашей кнопки основана на Widget.AppCompat.Button.Coloredцвете текста на кнопке по умолчанию белый!

но, кажется, есть проблема при отключении кнопки, кнопка изменит свой цвет на светло-серый, но цвет текста останется белым!

Обходной путь для этого - специально установить цвет текста на кнопке белым! как я сделал в стиле, показанном выше.

теперь вы можете просто определить свою кнопку и позволить AppCompat сделать все остальное :)

<Button
        android:layout_width="200dp"
        android:layout_height="48dp" />

Государство с ограниченными возможностями Неработающее состояние

Включенное состояние Включенное состояние

Редактировать:

Добавить <Button android:theme="@style/BrandButtonStyle"/>

Мухаммед Альфаифи
источник
19
Это лучший способ сделать это сейчас! Вы также можете использовать стиль на отдельных кнопках с помощью <Button android:theme="@style/BrandButtonStyle"/>. Он должен быть themeатрибутом и неstyle атрибут.
Мохлендо,
7
@ Muhammad Alfaifi У вас есть пример проекта или суть для этого? Я создал чистый проект, и он не работает: github.com/Bresiu/ThemeTest . В цветах кнопок Lolipop с акцентным цветом и в API v16 кнопка остается серой: i.imgur.com/EVwkpk2.png
Bresiu
4
Это сработало только при указании атрибута android: theme. Я не мог заставить стиль атрибута работать для меня с тегом кнопки.
Рэй Хантер
8
Используя библиотеку v23.1 lib, это не сработало правильно, оно всегда показывало цвет акцента как bg, а не как определенный, когда пытался установить его на всю тему
Патрик Фавр
3
Та же проблема здесь, на v23.1 отключенная кнопка имеет тот же цвет, что и активированная кнопка. очень расстраивает кто-нибудь выяснит это?
AhmedW
63

В библиотеке поддержки Android 22.1.0 Google сделал Buttonтонировку. Итак, еще один способ настроить цвет фона кнопки - это использоватьbackgroundTint атрибут.

Например,

<Button
       android:id="@+id/add_remove_button"
       android:layout_width="wrap_content"
       android:layout_height="wrap_content"
       android:backgroundTint="@color/bg_remove_btn_default"
       android:textColor="@android:color/white"
       tools:text="Remove" />
Манабу-GT
источник
1
В заключение! Сообщение в блоге о выпуске 22.1: android-developers.blogspot.no/2015/04/…
GuillermoMP
5
Документация гласит: «Это будет автоматически использоваться, когда вы используете Button в ваших макетах. Вам нужно только использовать этот класс вручную при написании пользовательских представлений». developer.android.com/reference/android/support/v7/widget/… означает ли это, что нам не нужно вручную изменять все наши макеты и код Java?
Стефан
@ Стефан нет, мы должны изменить макеты. chris.banes.me/2015/04/22/support-libraries-v22-1-0
Антон Головин
ЗДОРОВО! Теперь, есть AppCompatToggleButton, который позволяет вам изменять фон ToggleButtons? Может быть, я могу плагиат кода ...
заняться
19
К сожалению, это работает только на API 21+. Атрибут android: backgroundTint не работает на пред-Lollipop даже с библиотекой AppCompat. Только colorButtonNormal из темы работает на pre-Lollipop.
Timur_C
42

Для поддержки цветных кнопок используйте последнюю библиотеку AppCompat (> 23.2.1 ) с:

раздувать - XML

AppCompat Widget:

android.support.v7.widget.AppCompatButton

Стиль AppCompat:

style="@style/Widget.AppCompat.Button.Colored"

NB! Чтобы установить собственный цвет в xml: используйте attr: appвместоandroid

(использовать alt+enterили объявить xmlns:app="http://schemas.android.com/apk/res-auto"для использования app)

приложение : backgroundTint = "@ color / your_custom_color"

Пример:

<android.support.v7.widget.AppCompatButton
     style="@style/Widget.AppCompat.Button.Colored"
     app:backgroundTint="@color/your_custom_color"
     android:layout_width="wrap_content"
     android:layout_height="wrap_content"     
     android:text="Colored Button"/>

или установите его программно - JAVA

 ViewCompat.setBackgroundTintList(your_colored_button,
 ContextCompat.getColorStateList(getContext(),R.color.your_custom_color));
TouchBoarder
источник
Ваш Java-код работал на меня. А ответ Мухаммеда Альфаифи помог установить цвет текста кнопки.
Микро
Есть ли простой способ программно установить оттенок (не фон)?
хранилище
Чудесно! Работает и на 4.4.4! И состояние селектора также поддерживается довольно хорошо!
sud007 10.10.16
Согласно документам : Это автоматически используется при настройке кнопок в ваших макетах. Вам нужно только указать AppCompatButton при создании пользовательских представлений.
gMale
Интересно, что изменения XML отлично работали во фрагменте, но не в макете Activity. Кнопки Activity использовали только colorAccent. Программная версия работала, хотя.
Леон
25

С последней версией библиотеки поддержки вы можете просто унаследовать вашу активность AppCompatActivity, поэтому она будет раздувать ваш Buttonas AppCompatButtonи даст вам возможность стилизовать цвет каждой кнопки на макете с помощью of android:theme="@style/SomeButtonStyle", где SomeButtonStyle:

<style name="SomeButtonStyle" parent="@android:style/Widget.Button">
    <item name="colorButtonNormal">@color/example_color</item>
</style>

Работал у меня в 2.3.7, 4.4.1, 5.0.2

Артем
источник
Спасибо!!! Я просто изменил родительское значение для «Widget.AppCompat.EditText», так как мне нужно обновить стиль EditText.
Хуан Саравиа
3
Спасибо, сработало и у меня. Убедитесь, что используете android:themeи нет style. Вы также можете добавить colorControlHighlightи colorControlActivated.
Рейчел
не работает, API 22, AppCompatActivity, тема Material.Light
Андрей Углев
1
@AndreyUglev попробуйте Theme.AppCompat.Lightвместо этого.
Артем
Привет, он меняет нужный цвет, НО удаляет тени.
Amio.io
16

если вы хотите ниже стиля

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

добавить этот стиль вашей кнопки

style="@style/Widget.AppCompat.Button.Borderless.Colored"

если вы хотите этот стиль

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

добавить код ниже

style="@style/Widget.AppCompat.Button.Colored"
Jinu
источник
1
compile 'com.android.support:appcompat-v7:23.1.0'Вы должны добавить.
Пратик Бутани
1
но вопрос в том, как получить материальные кнопки с разными цветами, чтобы не у всех был основной цвет темы.
Apostrofix
15

Ответ в ТЕМЕ, а не в стиле

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

Создайте тему с помощью colorButtonNormal и colorPrimary:

<style name="ThemeAwesomeButtonColor" parent="AppTheme">
    <item name="colorPrimary">@color/awesomePrimaryColor</item>
    <item name="colorButtonNormal">@color/awesomeButtonColor</item>
</style>

Используйте эту тему в кнопке

<Button
        android:id="@+id/btn_awesome"
        style="@style/AppTheme.Button"
        android:theme="@style/ThemeAwesomeButtonColor"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/btn_awesome"/>

«AppTheme.Button» может быть любой вещью, расширяющей стиль кнопки, как здесь, я использую основной цвет для цвета текста:

<style name="AppTheme.Button" parent="Base.Widget.AppCompat.Button">
    ...
    <item name="android:textColor">?attr/colorPrimary</item>
    ...
</style>

И вы получите кнопку в любом цвете, который вы хотите, который совместим с дизайном материала.

lonelyboycs
источник
Какие еще атрибуты я могу добавить в стили.
Сагар Наяк
4

Я только что создал библиотеку Android, которая позволяет легко изменять цвет кнопки и цвет пульсации

https://github.com/xgc1986/RippleButton

<com.xgc1986.ripplebutton.widget.RippleButton
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:id="@+id/btn"
    android:text="Android button modified in layout"
    android:textColor="@android:color/white"
    app:buttonColor="@android:color/black"
    app:rippleColor="@android:color/white"/>

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

xgc1986
источник
4

эта работа для меня с appcompat-v7: 22.2.0 в Android + 4.0

в вашем styles.xml

<style name="Button.Tinted" parent="Widget.AppCompat.Button">
    <item name="colorButtonNormal">YOUR_TINT_COLOR</item>
    <item name="colorControlHighlight">@color/colorAccent</item>
    <item name="android:textColor">@android:color/white</item>
</style>

в вашем файле макета

<Button
    android:id="@+id/but_next"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:text="@string/but_continue"
    android:theme="@style/Button.Tinted" />
ingyesid
источник
Привет, он меняет нужный цвет, НО удаляет тени.
Amio.io
Привет еще раз, я вижу. Теперь это правильное поведение.
Amio.io
Как вы можете сделать это на Java?
Микро
@MicroR проверьте ответ выше.
ingyesid
4

Планировка:

<android.support.v7.widget.AppCompatButton
  style="@style/MyButton"
  ...
  />

styles.xml:

<style name="MyButton" parent="Widget.AppCompat.Button.Colored">
  <item name="backgroundTint">@color/button_background_selector</item>
  <item name="android:textColor">@color/button_text_selector</item>
</style>

цвет / button_background_selector.xml:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_enabled="false" android:color="#555555"/>
    <item android:color="#00ff00"/>
</selector>

цвет / button_text_selector.xml:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_enabled="false" android:color="#888888"/>
    <item android:color="#ffffff"/>
</selector>
BArtWell
источник
3

Для тех, кто использует ImageButtonвот как вы это делаете:

В style.xml:

<style name="BlueImageButton" parent="Base.Widget.AppCompat.ImageButton">
    <item name="colorButtonNormal">@color/primary</item>
    <item name="android:tint">@color/white</item>
</style>

в v21 / style.xml:

<style name="BlueImageButton" parent="Widget.AppCompat.ImageButton">
    <item name="android:colorButtonNormal">@color/primary</item>
    <item name="android:tint">@color/white</item>
</style>

Тогда в вашем файле макета:

<android.support.v7.widget.AppCompatImageButton
    android:id="@+id/my_button"
    android:theme="@style/BlueImageButton"
    android:layout_width="42dp"
    android:layout_height="42dp"
    android:layout_gravity="center_vertical"
    android:src="@drawable/ic_check_black_24dp"
    />
Микро
источник
Это помогло .... Думаю, важно отметить, что стиль кнопки применяется как тема, а не стиль в виджете «Кнопка». Я применял его под style = "@ style / BlueImageButton", и он не работал
velval
3

Если вы используете стилевое решение с colorButtonNormal , не забудьте наследовать от Widget.AppCompat.Button.Colored чтобы эффект ряби работал;)

подобно

<style name="CustomButtonStyle" parent="Widget.AppCompat.Button.Colored">
      <item name="colorButtonNormal">@android:color/white</item>
</style>
didi.yeah
источник
2

Еще одно простое решение с использованием AppCompatButton

<android.support.v7.widget.AppCompatButton
     android:layout_width="wrap_content"
     android:layout_height="wrap_content"
     style="@style/Widget.AppCompat.Button.Colored"
     app:backgroundTint="@color/red"
     android:text="UNINSTALL" />
Hanzyusuf
источник
2

Использование:

android:backgroundTint="@color/customColor"

Или даже :

android:background="@color/customColor"

и это даст пользовательский цвет кнопки.

SuKu
источник
1

Если вам нужна только кнопка «Плоский» материал, вы можете настроить их фон, используя атрибут selectableItemBackground, как описано здесь .

kiruwka
источник
Если вы не хотите менять какие-либо цвета «оттенка» или выбранные цвета, это определенно простое решение, чтобы получить обратную связь с помощью цветных кнопок. Спасибо!
Theblang
1

Чтобы изменить цвет одной кнопки

ViewCompat.setBackgroundTintList(button, getResources().getColorStateList(R.color.colorId));
Джейди Соланки
источник
1

Для меня проблема заключалась в том, что в Android 5.0 это не android:colorButtonNormalимело никакого эффекта, и фактически ни один элемент из темы (например android:colorAccent), но в Android 4.4.3, например, не делал. Проект был настроен с compileSdkVersionи targetSdkVersionна 22, поэтому я внес все изменения как @Muhammad Alfaifi sugessted, но в конце я заметил, что проблема заключалась в buildToolsVersion , который не был обновлен. Как только я перешел на 23.0.1 , все начинает работать почти как обычно. Теперь, по- android:colorButtonNormalпрежнему не имеет никакого эффекта, но, по крайней мере, кнопка реагирует наandroid:colorAccent , что для меня приемлемо.

Я надеюсь, что этот намек может кому-то помочь. Примечание: я применил стиль непосредственно к кнопке, поскольку кнопка android:theme=[...]также не имела эффекта.

Бьянка Даничук
источник
Вы почти нашли 100% правильный способ использования нового @ style / Widget.AppCompat.Button.Colored;) - см. Этот ответ stackoverflow.com/a/35811157/19733911
около
1

Один из способов сделать это позволяет вам указать на стиль, а НЕ на тему ВСЕХ кнопок в вашем приложении.
В themes.xml добавить тему

    <style name="Theme.MyApp.Button.Primary.Blue" parent="Widget.AppCompat.Button">
        <item name="colorButtonNormal">@color/someColor</item>
        <item name="android:textColorPrimary">@android:color/white</item>
    </style>

Сейчас в styles.xml добавлю

    <style name="MyApp.Button.Primary.Blue" parent="">
        <item name="android:theme">@style/Theme.MyApp.Button.Primary.Blue</item>
    </style>

Теперь в вашем макете просто укажите СТИЛЬ в вашей кнопке

    <Button
        ...
        style="@style/MyApp.Button.Primary.Blue"
        ...  />
Дуглас 'ДК' Кнудсен
источник
1

ОБНОВИТЬ

Используйте библиотеку поддержки дизайна (23.2.0) и appcompatwidgets, как показано ниже

В библиотеке поддержки Android 22.1 :

Это делается автоматически при накачивании макетов - замена Button на AppCompatButton, TextView на AppCompatTextView и т. Д., Чтобы каждый из них мог поддерживать тонирование. В этом выпуске эти виджеты с поддержкой оттенков теперь общедоступны, что позволяет поддерживать поддержку оттенков даже в том случае, если вам нужно создать подкласс одного из поддерживаемых виджетов.

Полный список виджетов с оттенком:

AppCompatAutoCompleteTextView
AppCompatButton
AppCompatCheckBox
AppCompatCheckedTextView
AppCompatEditText
AppCompatMultiAutoCompleteTextView
AppCompatRadioButton
AppCompatRatingBar
AppCompatSpinner
AppCompatTextView

Дизайн материала для устройств перед леденцом на палочке :

AppCompat (он же ActionBarCompat) начинался как бэкпорт API-интерфейса ActionBar Android 4.0 для устройств, работающих на Gingerbread, предоставляя общий уровень API поверх реализации с переносом данных и реализации платформы. AppCompat v21 предоставляет API и набор функций, актуальный для Android 5.0


Амит Вагела
источник
1

Если вы хотите использовать стиль AppCompat, такой как Widget.AppCompat.Button , Base.Widget.AppCompat.Button.Colored и т. Д., Вам необходимо использовать эти стили с совместимыми представлениями из библиотеки поддержки.

Приведенный ниже код не работает для устройств, предшествующих lolipop:

<Button
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   android:theme="@style/Widget.AppCompat.Button" />

Вам необходимо использовать AppCompatButton для включения стилей AppCompat:

<android.support.v7.widget.AppCompatButton
   android:layout_width="wrap_content"
   android:layout_height="wrap_content"
   android:theme="@style/Widget.AppCompat.Button" />
farukcankaya
источник
2
Разве виджеты для приложений не используются автоматически при накачке макетов XML? Я считаю, что ImageViewзаменяется на, AppCompatImageViewи это должно быть то же самое со всеми виджетами, которые имеют соответствующую AppCompatверсию.
d.aemon
Нет, если вы не нацелены на последнюю целевую версию, вам нужно определить android.support.v7.widget.AppCompatImageViewявно.
farukcankaya
Что вы подразумеваете под last target version@power?
d.aemon
1

Я использую это. Эффект ряби и работа тени при нажатии кнопки.

style.xml

<style name="Button.Red" parent="Widget.AppCompat.Button.Colored">
    <item name="android:textColor">@color/material_white</item>
    <item name="android:backgroundTint">@color/red</item>
</style>

Кнопка на макете:

<Button
        style="@style/Button.Red"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="@string/close"/>
Мета
источник
0

Я на самом деле не хотел изменений в моих пользовательских стилях кнопок, но, к сожалению, они больше не работали.

У моего приложения minSdkVersion 9, и все работало раньше.

Я не знаю почему, но так как я удалил андроид: до buttonStyle, кажется, снова работает

сейчас = работает:

<item name="buttonStyle">@style/ButtonmyTime</item>

до = только серые кнопки материала:

<item name="android:buttonStyle">@style/ButtonmyTime</item>

У меня нет специальной папки для новой версии Android, так как мои кнопки довольно плоские, и они должны выглядеть одинаково на всех версиях Android.

Может быть, кто-то может сказать мне, почему я должен был удалить «android:» ImageButton все еще работает с «android:»

<item name="android:imageButtonStyle">@style/ImageButtonmyTimeGreen</item>
Штефана
источник
0

После 2 дней поиска ответов у меня не работала тема кнопок в API <21.

Мое единственное решение состоит в том, чтобы переопределить тонирование AppCompatButton не только с основной темой приложения "colorButtonNormal", но и с видом backgroundTint следующим образом:

public class AppCompatColorButton extends AppCompatButton {

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

    public AppCompatColorButton(Context context, AttributeSet attrs) {
        this(context, attrs, android.support.v7.appcompat.R.attr.buttonStyle);
    }

    public AppCompatColorButton(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);

        if (TintManager.SHOULD_BE_USED) {
            setSupportBackgroundTintList(createButtonColorStateList(getContext(), attrs, defStyleAttr));
        }
    }

    static final int[] DISABLED_STATE_SET = new int[]{-android.R.attr.state_enabled};
    static final int[] FOCUSED_STATE_SET = new int[]{android.R.attr.state_focused};
    static final int[] PRESSED_STATE_SET = new int[]{android.R.attr.state_pressed};
    static final int[] EMPTY_STATE_SET = new int[0];

    private ColorStateList createButtonColorStateList(Context context, AttributeSet attrs, int defStyleAttr) {
        final int[][] states = new int[4][];
        final int[] colors = new int[4];
        int i = 0;

        final int themeColorButtonNormal = ThemeUtils.getThemeAttrColor(context, android.support.v7.appcompat.R.attr.colorButtonNormal);
        /*TypedArray a = context.obtainStyledAttributes(attrs, new int[] { android.R.attr.backgroundTint }, defStyleAttr, 0);
        final int colorButtonNormal = a.getColor(0, themeColorButtonNormal);*/
        TypedArray a = context.obtainStyledAttributes(attrs, android.support.v7.appcompat.R.styleable.View, defStyleAttr, 0);
        final int colorButtonNormal = a.getColor(android.support.v7.appcompat.R.styleable.View_backgroundTint, themeColorButtonNormal);
        a.recycle();
        final int colorControlHighlight = ThemeUtils.getThemeAttrColor(context, android.support.v7.appcompat.R.attr.colorControlHighlight);

        // Disabled state
        states[i] = DISABLED_STATE_SET;
        colors[i] = ThemeUtils.getDisabledThemeAttrColor(context, android.support.v7.appcompat.R.attr.colorButtonNormal);
        i++;

        states[i] = PRESSED_STATE_SET;
        colors[i] = ColorUtils.compositeColors(colorControlHighlight, colorButtonNormal);
        i++;

        states[i] = FOCUSED_STATE_SET;
        colors[i] = ColorUtils.compositeColors(colorControlHighlight, colorButtonNormal);
        i++;

        // Default enabled state
        states[i] = EMPTY_STATE_SET;
        colors[i] = colorButtonNormal;
        i++;

        return new ColorStateList(states, colors);
    }
}

Затем вы можете определить свой цвет кнопки следующим образом:

<com.example.views.AppCompatColorButton
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:backgroundTint="#ffff0000"
            app:backgroundTint="#ffff0000"
            android:text="Button"
            android:textColor="@android:color/white" />
Томас Г.
источник
0

Этот ТАК ответ помог мне прийти к ответу https://stackoverflow.com/a/30277424/3075340

Я использую этот метод утилиты, чтобы установить фоновый оттенок кнопки. Работает с устройствами перед леденцом на палочке:

// Set button background tint programmatically so it is compatible with pre-lollipop devices.
public static void setButtonBackgroundTintAppCompat(Button button, ColorStateList colorStateList){
    Drawable d = button.getBackground();
    if (button instanceof AppCompatButton) {
        // appcompat button replaces tint of its drawable background
        ((AppCompatButton)button).setSupportBackgroundTintList(colorStateList);
    } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
        // Lollipop button replaces tint of its drawable background
        // however it is not equal to d.setTintList(c)
        button.setBackgroundTintList(colorStateList);
    } else {
        // this should only happen if
        // * manually creating a Button instead of AppCompatButton
        // * LayoutInflater did not translate a Button to AppCompatButton
        d = DrawableCompat.wrap(d);
        DrawableCompat.setTintList(d, colorStateList);
        button.setBackgroundDrawable(d);
    }

}

Как использовать в коде:

Utility.setButtonBackgroundTintAppCompat(myButton,
ContextCompat.getColorStateList(mContext, R.color.your_custom_color));

Таким образом, вам не нужно указывать ColorStateList, если вы просто хотите изменить оттенок фона и ничего более, кроме того, чтобы поддерживать приятные эффекты кнопок, а что нет.

Микро
источник
0

Я поставил android:textColorна @nullмне кнопку темы , и это помогает.

styles.xml

<style name="Button.Base.Borderless" parent="Widget.AppCompat.Button.Borderless.Colored">
    <item name="android:textColor">@null</item>
</style>

some_layout.xml

<Button
    style="@style/Button.Base.Borderless"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="@string/hint" />

Теперь цвет текста кнопки colorAccentопределяется вAppTheme

<style name="AppTheme" parent="@style/Theme.AppCompat.Light.NoActionBar">
    <item name="colorAccent">@color/colorAccent</item>
    <item name="borderlessButtonStyle">@style/Button.Base.Borderless</item>
    <item name="alertDialogTheme">@style/AlertDialog</item>
</style>
Денис Рыбников
источник
0

Если вы используете kotlin, вы можете видеть, что все атрибуты из MaterialButton поддерживаются. Не используйте атрибут android: background. MaterialButton управляет своим собственным фоном, который можно нарисовать, а установка нового фона означает, что цвет кнопки «Отключить материал» больше не может гарантировать правильную работу новых атрибутов, которые он вводит. Если фон по умолчанию изменен, Material Button не может гарантировать четкое поведение. На MainActivity.kt

class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        buttonClick.setOnClickListener {
            (it as MaterialButton).apply {
                backgroundTintList = ColorStateList.valueOf(Color.YELLOW)
                backgroundTintMode = PorterDuff.Mode.SRC_ATOP
            }
        }
    }
}

На Activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.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:id="@+id/constraintLayout"
    tools:context=".MainActivity">
    <com.google.android.material.button.MaterialButton
        android:id="@+id/buttonNormal"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="24dp"
        android:text="Material Button Normal"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toTopOf="parent" />
    <com.google.android.material.button.MaterialButton
        android:id="@+id/buttonTint"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="16dp"
        android:backgroundTint="#D3212D"
        android:text="Material Button Background Red"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/buttonNormal" />
    <com.google.android.material.button.MaterialButton
        android:id="@+id/buttonTintMode"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="16dp"
        android:backgroundTint="#D3212D"
        android:backgroundTintMode="multiply"
        android:text="Tint Red + Mode Multiply"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/buttonTint" />
    <com.google.android.material.button.MaterialButton
        android:id="@+id/buttonClick"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_marginTop="32dp"
        android:text="Click To Change Background"
        app:layout_constraintEnd_toEndOf="parent"
        app:layout_constraintHorizontal_bias="0.498"
        app:layout_constraintStart_toStartOf="parent"
        app:layout_constraintTop_toBottomOf="@+id/buttonTintMode" />
</androidx.constraintlayout.widget.ConstraintLayout>

ресурс: Пример изменения цвета кнопки материала

Tienanhvn
источник
0

если вы хотите сделать это с помощью кода любого цвета, используйте это:

DrawableCompat.setTintList(button.getBackground(), ColorStateList.valueOf(yourColor));
Амир Хоссейн Гасеми
источник