Як зробити кругову пульсацію на кнопці при натисканні на неї?


121

Фон

У додатку для набору номерів Android, коли ви починаєте щось шукати, і натискаєте кнопку стрілки зліва від EditText, ви отримуєте ефект кругової пульсації:

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

Проблема

Я також намагався це мати, але у мене вийшов прямокутний:

    <ImageButton
        android:id="@+id/navButton"
        android:layout_width="40dp"
        android:layout_height="40dp"
        android:layout_gravity="center_vertical"
        android:layout_marginLeft="8dp"
        android:background="?android:attr/selectableItemBackground"
        android:src="@drawable/search_ic_back_arrow"/>

Питання

Як зробити так, щоб кнопка мала ефект кругової пульсації при натисканні на неї? Чи потрібно створити нову черпальну версію, чи є така можливість побудована для цього?



Можливий відповідь тут stackoverflow.com/questions/33477025 / ...
Amrish Kakadiya

1
Подумайте про зміну вибраної відповіді на таку, яка має найбільше оновлень, оскільки це фактично вирішує проблему
Джефф Баргер

@JeffBarger Чому? Обидва працюють добре. Між ними немає кращого.
андроїд розробник

Відповіді:


17

Якщо у вас вже є фонове зображення, ось приклад пульсації, який виглядає близьким до selectableItemBackgroundBorderless:

            <ImageButton
                android:id="@+id/btn_show_filter_dialog"
                android:layout_width="24dp"
                android:layout_height="24dp"
                android:background="@drawable/ic_filter_state"/>

ic_filter_state.xml:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item
        android:state_pressed="true"
        android:state_enabled="true"
        android:drawable="@drawable/state_pressed_ripple"/>
    <item
        android:state_enabled="true"
        android:drawable="@drawable/ic_filter" />
</selector>

state_pression_ripple.xml: (непрозорість встановлена ​​на білому тлі 10%) 1AFFFFFF

 <?xml version="1.0" encoding="UTF-8"?>    
    <ripple xmlns:android="http://schemas.android.com/apk/res/android">
        <item>
            <shape android:shape="oval">
                <solid android:color="#1AFFFFFF"/>
            </shape>
            <color android:color="#FFF"/>
        </item>
    </ripple>

287

Якщо ви використовуєте тему AppCompat, ви можете встановити фон перегляду як:

android:background="?selectableItemBackgroundBorderless"

Це додасть кругової пульсації на 21 і вище, а квадратний фон нижче 21.


Приємно. Чи можу я також якось задати його колір?
андроїд розробник

4
в API 23 фон "вгору" виявляється вдвічі меншим порівняно з selectbleItemBackgroundBorderless
snodnipper

3
Гарна, найкраща відповідь. ty
Skywalker

1
@androiddeveloper, колір можна встановити, встановивши colorControlHighlight, як показано нижче у ваших стилях.xml <item name = "colorControlHighlight"> # F00 </item>
облігація

3
Якщо ви використовуєте його всередині інших макетів, вам може знадобитися і android:clipChildren="false"в макетах, щоб дозволити анімації поширюватися.
Танасіс

83

Ще один атрибут з ефектом круглої пульсації, спеціально для панелі дій:

android:background="?actionBarItemBackground"

UPD : колір Ripple можна змінити за цим атрибутом:

<!--somewhere in styles-->
<item name="colorControlHighlight">your_color_here</item>

Але майте на увазі, цей атрибут застосовується до всіх ефектів пульсацій за замовчуванням.


Будь-який спосіб налаштувати його? Наприклад, колір? Може щось у стилях? Або ще конкретніше у самому тезі XML перегляду?
андроїд розробник

Не знаю, сьогодні я вирішив цю проблему, і відповіді вище не спрацювали так, як потрібно. Я припускаю, що колір можна налаштувати під стилі, але точно не в образі.
Анріміан

1
Це саме той правильний ефект, який я шукаю. До речі, ви можете згадати, де знайти цей атрибут, здається, це не задокументовано.
Джек Ван

2
Відповідає на питання ОП. Ви повинні бути позначені як найкраща відповідь. +1
Корбелла

2
@MeysamHadigheh ?- це ярлик для?attr/
musooff

47

Створіть і встановіть пульсацію, що малюється як фон. Щось на зразок цього.

<?xml version="1.0" encoding="utf-8"?>
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
    android:color="@color/grey_15">
    <item android:id="@android:id/mask">
        <shape android:shape="oval">
            <solid android:color="?android:colorPrimary"/>
        </shape>
        <color android:color="@color/white"/>
    </item>
</ripple>

Це щось у моєму коді. Ви можете використовувати свої кольори :)
Thomas R.

Як я можу використовувати селектор за замовчуванням у випадку, якщо він знаходиться на попередньому Lollipop? Також він використовує ті ж кольори, що і на набірника?
андроїд розробник

2
Ви можете помістити пульсацію, що виводиться в папку drawables-v21. А для попереднього використання використовуйте простий конвеєрний стан. Використовуйте те саме ім’я файлу і введіть його в папку, що виводиться (за замовчуванням).
Томас Р.

2
Ви також можете створити стиль. У папці значень-v21 створіть новий стиль і встановіть пульсацію, що малюється як фон. А для попереднього L, тобто у вашій папці значень styles.xml в якості фону поставте атрибут "selectableItemBackground" для того ж стилю.
Томас Р.

1
Якщо ви бажаєте того ж кольору пульсації, що і інші ефекти пульсації за замовчуванням, які використовуються в додатку, використовуйте "? Attr / colorControlHighlight" як колір.
alexbchr


18

Ви можете створити пульсацію кола для малювання за допомогою android:radiusатрибута в xml.

Приклад:

<ripple xmlns:android="http://schemas.android.com/apk/res/android"
    android:color="your_color"
    android:radius="your_radius" />

Зверніть увагу, що ваш your_radiusрозмір повинен бути меншим за ширину та висоту зору. Наприклад: якщо у вас перегляд, розмір 60dp x 60dp your_radiusповинен бути близьким 30dp(ширина / 2 або висота / 2).

Працюйте на Android 5.0 і вище.


3

Якщо ви хочете отримати більш загальні XML-файли, у мене є два файли:

1) btn_ripple_background з кодом:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item
    android:state_pressed="true"
    android:state_enabled="true"
    android:drawable="@drawable/ripple_circular_shape"/>
</selector>

2) ripple_circuler_shape з кодом:

<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
    android:color="@color/btn_state_pressed_text_color"
    android:shape="oval">
    <solid android:color="@color/btn_state_pressed_text_color" />
</shape>

нарешті використання:android:foreground="@drawable/ripple_btn_background"


1

Спробуйте:

android:background="@android:color/transparent"
android:clickable="true"
android:focusable="true"
android:foreground="?actionBarItemBackground"

1
Будь ласка, не публікуйте лише код як відповідь, але додайте пояснення, що робить ваш код та як він вирішує проблему. Відповіді з поясненням, як правило, вищої якості і, швидше за все, залучають репутацію.
Марк Ротвевель

Плавніше, ніж встановити actionBarItemBackground як фон. Але все ще не зовсім так само, як сама анімаційна смужка дій.
coolcool1994

1

Якщо ви хочете, щоб ефект пульсації не перейшов межу кола, ви можете перевірити цей код. Це працює на мене бездоганно. Просто пам’ятайте, ви повинні дати id = @ android: id / mask в ripple_blue.xml

<ImageButton
    android:id="@+id/send_password_to_mail_image_view"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:background="@drawable/ripple_blue"
    android:src="@drawable/ic_filter" />

ripple_blue.xml

<ripple
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:color="@color/colorRipple">

    <item android:id="@android:id/mask">

        <shape android:shape="oval">
            <solid android:color="@color/colorWindowBackground"/>
        </shape>

    </item>

    <item android:id="@android:id/background">

        <shape android:shape="oval">
            <solid android:color="@color/colorWindowBackground"/>
        </shape>

    </item>

</ripple>

color.xml

<resources xmlns:tools="http://schemas.android.com/tools">
    <color name="colorWindowBackground">#F2F5FC</color>
    <color name="colorRipple">#0288d1</color>
</resources>


0

У Kotlin / Java ви можете зробити наступне

fun View.applyCircularRippleEffect() {
    val backgroundResId = context.getResource(android.R.attr.actionBarItemBackground)

    if (backgroundResId != 0) {
        setBackgroundResource(backgroundResId)
        isClickable = true
        isFocusable = true
    }
}

// getResource extension
fun Context.getResource(resourceId: Int): Int {
    val out = TypedValue()
    theme.resolveAttribute(resourceId, out, true)

    return out.resourceId
}

context.getResource не знайдено
Рахул Мандалія

@RahulMandaliya дякую за коментар. Моє погано, це був мій власний метод розширення. Додав його до відповіді
mihails.kuzmins
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.