699 votos

Estándar de Android Botón con un color diferente

Me gustaría cambiar el color de un estándar de Android botón ligeramente para adaptarse mejor a un cliente de la marca. Por ejemplo, vea la "Mesa" para el OpenTable aplicación:

alt text

La mejor manera que he encontrado para hacer esto hasta el momento es cambiar el Button's dibujable a la siguiente desplegable situado en res/drawable/red_button.xml:

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

Pero esto requiere que crear tres diferentes objetos dibujables para cada uno de los botones quiero personalizar (uno para el botón en reposo, uno cuando está centrado, y uno cuando se pulsa). Que parece más complicado y no SECO que necesito.

Todo lo que realmente quiero hacer es aplicar algún tipo de transformación de color para el botón. ¿Hay una manera más fácil de ir acerca de cómo cambiar un botón de color que estoy haciendo?

704voto

emmby Puntos 35359

Descubrí que todo esto se puede hacer en un archivo de forma bastante sencilla. Poner algo como el código siguiente en un archivo con el nombre custom_button.xml y, a continuación, establezca background="@drawable/custom_button" en el botón de vista:

<?xml version="1.0" encoding="utf-8"?>
<selector
    xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:state_pressed="true" >
        <shape>
            <gradient
                android:startColor="@color/yellow1"
                android:endColor="@color/yellow2"
                android:angle="270" />
            <stroke
                android:width="3dp"
                android:color="@color/grey05" />
            <corners
                android:radius="3dp" />
            <padding
                android:left="10dp"
                android:top="10dp"
                android:right="10dp"
                android:bottom="10dp" />
        </shape>
    </item>

    <item android:state_focused="true" >
        <shape>
            <gradient
                android:endColor="@color/orange4"
                android:startColor="@color/orange5"
                android:angle="270" />
            <stroke
                android:width="3dp"
                android:color="@color/grey05" />
            <corners
                android:radius="3dp" />
            <padding
                android:left="10dp"
                android:top="10dp"
                android:right="10dp"
                android:bottom="10dp" />
        </shape>
    </item>

    <item>        
        <shape>
            <gradient
                android:endColor="@color/blue2"
                android:startColor="@color/blue25"
                android:angle="270" />
            <stroke
                android:width="3dp"
                android:color="@color/grey05" />
            <corners
                android:radius="3dp" />
            <padding
                android:left="10dp"
                android:top="10dp"
                android:right="10dp"
                android:bottom="10dp" />
        </shape>
    </item>
</selector>

302voto

conjugatedirection Puntos 2134

Después de Tomasz la respuesta, también puede establecer mediante programación la sombra de la totalidad de botón usando el PorterDuff modo multiplicar. Esto va a cambiar el botón de color en vez de sólo la tinta.

Si usted comienza con un estándar de sombra gris botón:

button.getBackground().setColorFilter(0xFFFF0000, PorterDuff.Mode.MULTIPLY);

le dará una sombra de color rojo botón,

button.getBackground().setColorFilter(0xFF00FF00, PorterDuff.Mode.MULTIPLY);

le dará una sombreada de verde botón, etc., donde el primer valor es el color en formato hexadecimal.

Funciona mediante la multiplicación de la actual botón de color valor por su valor de color. Estoy seguro de que también hay un montón más que se puede hacer con estos modos.

145voto

Tomasz Puntos 1817

Mike, usted podría estar interesado en los filtros de color.

Un ejemplo:

button.getBackground().setColorFilter(new LightingColorFilter(0xFFFFFFFF, 0xFFAA0000));

intente esto para lograr el color que desee.

22voto

Stan Kurdziel Puntos 1603

Me gusta el color filtro de sugerencia en respuestas anteriores de @conjugatedirection y @Tomasz; sin Embargo, he encontrado que el código proporcionado hasta ahora no era tan fácil de aplicar como yo esperaba.

En primer lugar, no se mencionó en donde aplicar y limpiar el filtro de color. Es posible que haya otros buenos lugares para hacerlo, pero lo que me vino a mi mente fue un OnTouchListener.

A partir de mi lectura de la pregunta original, la solución ideal sería uno que no conlleva ningún tipo de imágenes. La respuesta usando aceptadas custom_button.xml desde @emmby es probablemente un mejor ajuste de los filtros de color si ese es tu objetivo. En mi caso, estoy empezando con una imagen png de un diseñador de interfaz de usuario de lo que el botón se supone que se parecen. Si puedo configurar el botón de fondo de esta imagen, el valor predeterminado de relieve la retroalimentación se pierde por completo. Este código sustituye a que el comportamiento de los programas oscurecimiento efecto.

button.setOnTouchListener(new OnTouchListener() {
    @Override
    public boolean onTouch(View v, MotionEvent event) {
        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                // 0x6D6D6D sets how much to darken - tweak as desired
                setColorFilter(v, 0x6D6D6D);
                break;
            // remove the filter when moving off the button
            // the same way a selector implementation would 
            case MotionEvent.ACTION_MOVE:
                Rect r = new Rect();
                v.getLocalVisibleRect(r);
                if (!r.contains((int) event.getX(), (int) event.getY())) {
                    setColorFilter(v, null);
                }
                break;
            case MotionEvent.ACTION_OUTSIDE:
            case MotionEvent.ACTION_CANCEL:
            case MotionEvent.ACTION_UP:
                setColorFilter(v, null);
                break;
        }
        return false;
    }

    private void setColorFilter(View v, Integer filter) {
        if (filter == null) v.getBackground().clearColorFilter();
        else {
            // To lighten instead of darken, try this:
            // LightingColorFilter lighten = new LightingColorFilter(0xFFFFFF, filter);
            LightingColorFilter darken = new LightingColorFilter(filter, 0x000000);
            v.getBackground().setColorFilter(darken);
        }
        // required on Android 2.3.7 for filter change to take effect (but not on 4.0.4)
        v.getBackground().invalidateSelf();
    }
});

He extraído esta como una clase separada para su aplicación a múltiples botones de muestra como anónimo interior de la clase sólo para hacerme a la idea.

16voto

haemish Puntos 271

Si usted está haciendo botones de color con el XML usted puede hacer que el código sea un poco más limpio especificando el centrado y el estado presionado en un archivo separado y volver a usarlos. Mi botón verde se parece a esto:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:state_focused="true" android:drawable="@drawable/button_focused"/>
    <item android:state_pressed="true" android:drawable="@drawable/button_pressed"/>

    <item>
        <shape>
            <gradient android:startColor="#ff00ff00" android:endColor="#bb00ff00" android:angle="270" />
            <stroke android:width="1dp" android:color="#bb00ff00" />
            <corners android:radius="3dp" />
            <padding android:left="10dp" android:top="10dp" android:right="10dp" android:bottom="10dp" />
        </shape>
    </item>

</selector>

Iteramos.com

Iteramos es una comunidad de desarrolladores que busca expandir el conocimiento de la programación mas allá del inglés.
Tenemos una gran cantidad de contenido, y también puedes hacer tus propias preguntas o resolver las de los demás.

Powered by:

X