¿Cómo puedo dar un efecto de clic de vista de imagen como un botón en Android?

84

Tengo imageview en mi aplicación de Android que estoy usando como un botón con el evento onClick dado, pero como puede adivinar, no le da a imageview un efecto en el que se puede hacer clic cuando se hace clic. ¿Cómo puedo lograrlo?

Burak Dede
fuente

Respuestas:

53

Puede diseñar diferentes imágenes para estados en los que se hizo clic o en los que no se hizo clic y configurarlas en onTouchListener de la siguiente manera

final ImageView v = (ImageView) findViewById(R.id.button0);
        v.setOnTouchListener(new OnTouchListener() {
            @Override
            public boolean onTouch(View arg0, MotionEvent arg1) {
                switch (arg1.getAction()) {
                case MotionEvent.ACTION_DOWN: {
                    v.setImageBitmap(res.getDrawable(R.drawable.img_down));
                    break;
                }
                case MotionEvent.ACTION_CANCEL:{
                    v.setImageBitmap(res.getDrawable(R.drawable.img_up));
                    break;
                }
                }
                return true;
            }
        });

La mejor opción es definir un selector de la siguiente manera

<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_selected="true"   
        android:drawable="@drawable/img_down" />
    <item android:state_selected="false"   
        android:drawable="@drawable/img_up" />
</selector>

y seleccione la imagen en el evento:

v.setOnTouchListener(new OnTouchListener() {
            @Override
            public boolean onTouch(View arg0, MotionEvent arg1) {
                v.setSelected(arg1.getAction()==MotionEvent.ACTION_DOWN);
                return true;
            }
        });
Martin Booka Weser
fuente
1
¿Puedes explicar qué res.getDrawable res qué hace?
VenushkaT
v.setSelected solo == true una vez, y se mueve inmediatamente a falso debido a MotionEvent.ACTION_MOVE. Una vez que se suelta el dedo, se produce MotionEvent.ACTION_UP. Si usa el método de selector, use una lógica separada para setSelected o setPressed. if (arg1.getAction () == MotionEvent.ACTION_DOWN) {v.setPressed (verdadero); } else if (arg1.getAction () == MotionEvent.ACTION_UP) {v.setPressed (falso); }
Adam Denoon
Es mejor MotionEvent.ACTION_DOWN || MotionEvent.ACTION_MOVEmantener la imagen visible mientras estemos presionando.
Alaa M.
No es necesario setOnTouchListener(.... Simplemente puede crear el <selector ...>y luego configurar el ImageView en el que se puede hacer clic en XML como<ImageView ... android:clickable="true" android:focusable="true" android:src="@drawable/my_selector" />
Pierre
76

Puede hacer esto con una sola imagen usando algo como esto:

     //get the image view
    ImageView imageView = (ImageView)findViewById(R.id.ImageView);

    //set the ontouch listener
    imageView.setOnTouchListener(new OnTouchListener() {

        @Override
        public boolean onTouch(View v, MotionEvent event) {

            switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN: {
                    ImageView view = (ImageView) v;
                    //overlay is black with transparency of 0x77 (119)
                    view.getDrawable().setColorFilter(0x77000000,PorterDuff.Mode.SRC_ATOP);
                    view.invalidate();
                    break;
                }
                case MotionEvent.ACTION_UP:
                case MotionEvent.ACTION_CANCEL: {
                    ImageView view = (ImageView) v;
                    //clear the overlay
                    view.getDrawable().clearColorFilter();
                    view.invalidate();
                    break;
                }
            }

            return false;
        }
    });

Probablemente convertiré esto en una subclase de ImageView (o ImageButton, ya que también es una subclase de ImageView) para facilitar su reutilización, pero esto debería permitirle aplicar un aspecto "seleccionado" a una vista de imagen.

Sr. Zorn
fuente
2
También agregué un caso para ACTION_CANCEL, funciona muy bien, ¡gracias!
Alan
Buena decisión: lo había agregado yo mismo en mi propio código, pero también lo actualizaré aquí.
Mr Zorn
1
Esta puede ser otra pregunta, pero ¿cómo cancelaría después de ACTION_UP? Específicamente ... El usuario golpea la imagen. El usuario arrastra el dedo fuera de la imagen para cancelar. Pero la acción no se cancela con este código
sudocoder
También agregaré MotionEvent.ACTION_OUTSIDE;)
bonnyz
3
es posible que desee regresar false, de lo contrario, el onClick()evento real de la vista no se activará
Nimrod Dayan
45

Es posible hacerlo con un solo archivo de imagen usando el método ColorFilter. Sin embargo, ColorFilter espera trabajar con ImageViews y no con Buttons, por lo que debe transformar sus botones en ImageViews. Esto no es un problema si está usando imágenes como sus botones de todos modos, pero es más molesto si tiene texto ... De todos modos, suponiendo que encuentre una forma de solucionar el problema con el texto, aquí está el código que debe usar:

ImageView button = (ImageView) findViewById(R.id.button);
button.setColorFilter(0xFFFF0000, PorterDuff.Mode.MULTIPLY);

Eso aplica una superposición roja al botón (el código de color es el código hexadecimal para el rojo completamente opaco; los primeros dos dígitos son transparencia, luego es RR GG BB).

ARIZONA_
fuente
3
¿Podría explicar qué sucederá después de que se ejecute ese código y dónde se pretende llamarlo? Intenté llamar a estas 2 líneas en la inicialización de imageView: pinta mi imagen en rojo y no sucede nada, ni al hacer clic ni al tacto. Lo mismo al llamar al tacto.
esteewhy
45

EDITAR : Aunque la respuesta original a continuación funciona y es fácil de configurar, consulte esta publicación de un Defensor de desarrolladores de Android en Google si desea / necesita una implementación más eficiente. También tenga en cuenta que el android:foregroundatributo llega a todas las vistas , incluido ImageView, de forma predeterminada en Android M.


El problema con el uso de un selector para un ImageView es que solo puede configurarlo como fondo de la vista; siempre que su imagen sea opaca, no verá el efecto del selector detrás de ella.

El truco consiste en envolver su ImageView en un FrameLayout con el atributo android:foregroundque nos permite definir una superposición para su contenido. Si configuramos android:foregroundun selector (por ejemplo, ?android:attr/selectableItemBackgroundpara el nivel de API 11+) y adjuntamos el OnClickListenerFrameLayout en lugar de ImageView, la imagen se superpondrá con el dibujable de nuestro selector: ¡el efecto de clic que deseamos!

Mirad:

<FrameLayout
    android:id="@+id/imageButton"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:foreground="?android:attr/selectableItemBackground" >

    <ImageView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:src="@drawable/yourImageFile" />

</FrameLayout>

(Tenga en cuenta que esto debe colocarse dentro de su diseño principal).

final View imageButton = findViewById(R.id.imageButton);
imageButton.setOnClickListener(new OnClickListener(){
    @Override
    public void onClick(View view) {
        // do whatever we wish!
    }
});
justasmo
fuente
2
Excelente ! Ésta es una muy buena solución. Misma solución utilizada en la aplicación de contactos para acciones de SMS o llamadas.
Jerry
¿No funcionará en API <11.? Android: attr / selectableItemBackground requiere API nivel 11 (el mínimo actual es 8)
MSaudi
El selectableItemBackgroundatributo solo se agregó en el nivel de API 11, por lo que debe usar otro selector si desea usar esta solución para niveles de API anteriores. Por ejemplo, para una de mis aplicaciones que admite API nivel 7, uso el @drawable/list_selector_holo_lightrecurso generado con la herramienta Android Holo Colors Generator .
justasm
¡Puede lograr el mismo comportamiento usando solo 1 <ImageButton>con selectableItemBackground!
Yohan Dahmani
28

Utilice style = "? Android: borderlessButtonStyle" en el archivo XML. Mostrará el efecto de clic predeterminado de Android.

<ImageView
    android:id="@+id/imageView1"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_launcher" 
    style="?android:borderlessButtonStyle"
/>
Anjula
fuente
1
Esta es en realidad la mejor respuesta, MUCHO más fácil
FrankMonza
1
Esto establece el relleno, e incluso si establece el relleno en 0, si la imagen que le da toma el imageView completo, no verá ningún efecto de hacer clic.
desarrollador de Android
2
@androiddeveloper se usa android:adjustViewBounds="true"para desarmar el relleno.
Hafez Divandari
1
Se recomienda usar style="?android:attr/borderlessButtonStyle": developer.android.com/guide/topics/ui/controls/…
Hafez Divandari
21

Simplemente use un ImageButton .

Kevin Coppock
fuente
3
Personalmente, no puedo hacer que se vea como ImageView. Sin borde, estire la imagen al tamaño de ImageButton, etc. Si puede dar este problema de borde y estiramiento, actualice su publicación.
Mi
15

Aquí está mi forma sencilla de resolver eso:

ImageView iv = (ImageView) findViewById(R.id.imageView);

iv.setOnClickListener(new OnClickListener() {

    @Override
    public void onClick(View arg0) {
        // TODO Auto-generated method stub
        //Agrega porcentajes de cada fraccion de grafica pastel

        Animation animFadein = AnimationUtils.loadAnimation(getApplicationContext(),R.anim.fade_in);

        iv.startAnimation(animFadein);
    });

En archivo res/anim/fade_in.xml:

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

<alpha
    android:duration="100"
    android:fromAlpha="0.0"
    android:interpolator="@android:anim/accelerate_interpolator"
    android:toAlpha="1.0" />
 </set>
Oscar Josue Alvrez
fuente
Gran solución, ¡gracias! Me desplacé por esta publicación probando todas las concisas, y no tuve éxito. Finalmente llegué aquí y funcionó para mí. Una observación: si tiene más de 2 botones hacia los que desea aplicar la animación ... para mi código, descubrí que necesito crear una instancia única de objeto Animation para cada botón al que quería aplicar el efecto. La reutilización de la misma instancia hizo que todos los botones parpadearan cuando se hacía clic en 1.
Gene Bo
9

Establezca el fondo seleccionable en ImageView y agregue algo de relleno. Luego adjunte el OnClickListener.

<ImageView
    android:id="@+id/your_image_view"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/your_image"
    android:padding="10dp"
    android:background="?android:attr/selectableItemBackground"/>
Oliver Kranz
fuente
¿Hay alguna manera de usarlo sin configurar el relleno y hacer que todo ImageView tenga el efecto y no solo el área vacía?
desarrollador de Android
Esto mostrará rizado en cúbicos, necesitamos rizado central
Kishan Solanki
8

Para definir la opción dibujable del selector

<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_selected="true"   
        android:drawable="@drawable/img_down" />
    <item android:state_selected="false"   
        android:drawable="@drawable/img_up" />
</selector>

Tengo que usar android: state_pressed en lugar de android: state_selected

<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed ="true"   
        android:drawable="@drawable/img_down" />
    <item android:state_pressed ="false"   
        android:drawable="@drawable/img_up" />
</selector>
worawee.s
fuente
5

Puede intentar android:background="@android:drawable/list_selector_background" obtener el mismo efecto que "Agregar alarma" en el "Reloj despertador" predeterminado (ahora Reloj de escritorio).

Marco Bettiol
fuente
5

Si desea ondulación cuando se toca, se puede dar con este código:

<ImageView
    ...
    android:background="?attr/selectableItemBackgroundBorderless"
    android:clickable="true"
    ...
</ImageView>

Del mismo modo, puede implementar el efecto de clic para TextView

<TextView
    ...
    android:background="?attr/selectableItemBackgroundBorderless"
    android:clickable="true"
    ...
</TextView>
npk
fuente
4

Esto funcionó para mí:

img.setOnTouchListener(new OnTouchListener(){

            @Override
            public boolean onTouch(View v, MotionEvent event) {
                switch (event.getAction())
                {
                    case MotionEvent.ACTION_DOWN:
                    {
                        ((ImageView)v).setImageAlpha(200);
                        break;
                    }
                    case MotionEvent.ACTION_MOVE:
                    {
                        // if inside bounds
                        if(event.getX() > 0 && event.getX() < v.getWidth() && event.getY() > 0 && event.getY() < v.getHeight())
                        {
                            ((ImageView)v).setImageAlpha(200);
                        }
                        else
                        {
                            ((ImageView)v).setImageAlpha(255);
                        }

                        break;
                    }
                    case MotionEvent.ACTION_UP:
                    {
                        ((ImageView)v).setImageAlpha(255);
                    }
                }
                return true;
            }

        });

@Editar: Como dijo Gunhan, habrá un problema de compatibilidad con el método setImageAlpha. Usé este método:

public static void setImageAlpha(ImageView img, int alpha)
    {
        if(Build.VERSION.SDK_INT > 15)
        {
            img.setImageAlpha(alpha);
        }
        else
        {
            img.setAlpha(alpha);
        }
    }
altosh
fuente
1
setImageAlpha requiere API nivel 16. Por lo tanto, para aplicaciones compatibles con versiones anteriores no es posible usarlo
Gunhan
1
@Gunhan en realidad, puede usar la biblioteca "nineOldAndroids" que permite usar alfa incluso en API más antiguas. simplemente use: ViewHelper.setAlpha (vista, alfa);
desarrollador de Android
4

Hago algunas cosas similares. Veo conveniente para ti o no.

Ver Asistente de efectos de prensa:

  • uso: haz un simple efecto de prensa como iOS

    Uso simple:

  • ImageView img = (ImageView) findViewById (R.id.img);

  • ViewPressEffectHelper.attach (img)

https://gist.github.com/extralam/7489370

Ah Lam
fuente
4

En combinación con todas las respuestas anteriores, quería presionar ImageView y cambiar de estado, pero si el usuario se movía, entonces "cancela" y no realiza un onClickListener.

Terminé haciendo un objeto Point dentro de la clase y estableciendo sus coordenadas de acuerdo con el momento en que el usuario presionó el ImageView. En MotionEvent.ACTION_UP grabé un nuevo punto y comparé los puntos.

Solo puedo explicarlo muy bien, pero esto es lo que hice.

// set the ontouch listener
weatherView.setOnTouchListener(new OnTouchListener() {

    @Override
    public boolean onTouch(View v, MotionEvent event) {
        // Determine what action with a switch statement
        switch (event.getAction()) {

        // User presses down on the ImageView, record the original point
        // and set the color filter
        case MotionEvent.ACTION_DOWN: {
            ImageView view = (ImageView) v;

            // overlay is black with transparency of 0x77 (119)
            view.getDrawable().setColorFilter(0x77000000,
                    PorterDuff.Mode.SRC_ATOP);
            view.invalidate();

            p = new Point((int) event.getX(), (int) event.getY());
            break;
        }

        // Once the user releases, record new point then compare the
        // difference, if within a certain range perform onCLick
        // and or otherwise clear the color filter
        case MotionEvent.ACTION_UP: {
            ImageView view = (ImageView) v;
            Point f = new Point((int) event.getX(), (int) event.getY());
            if ((Math.abs(f.x - p.x) < 15)
                    && ((Math.abs(f.x - p.x) < 15))) {
                view.performClick();
            }
            // clear the overlay
            view.getDrawable().clearColorFilter();
            view.invalidate();
            break;
        }
        }
        return true;
    }
});

Tengo un onClickListener configurado en imageView, pero esto puede ser un método.

samschwartz96
fuente
agregando mayúsculas y minúsculas MotionEvent.ACTION_CANCELcon la misma funcionalidad que MotionEvent.ACTION_UPentonces es posible "borrar" la vista si los usuarios realizan un "arrastre" que no es una acción de clic.
Mando Stam
4

Puede anular setPresseden ImageView y hacer el filtrado de color allí, en lugar de crear oyentes onTouchEvent:

@Override
public void setPressed(boolean pressed) {
    super.setPressed(pressed);

    if(getDrawable() == null)
        return;

    if(pressed) {
        getDrawable().setColorFilter(0x44000000, PorterDuff.Mode.SRC_ATOP);
        invalidate();
    }
    else {
        getDrawable().clearColorFilter();
        invalidate();
    }
}
ono
fuente
4

Según la respuesta del Sr.Zorn , utilizo un método estático en mi clase de utilidad abstracta:

public abstract class Utility {
...

    public static View.OnTouchListener imgPress(){
        return imgPress(0x77eeddff); //DEFAULT color
    }

    public static View.OnTouchListener imgPress(final int color){
        return new View.OnTouchListener() {

            @Override
            public boolean onTouch(View v, MotionEvent event) {

                switch(event.getAction()) {

                    case MotionEvent.ACTION_DOWN: {
                        ImageView view = (ImageView) v;
                        view.getDrawable().setColorFilter(color, PorterDuff.Mode.SRC_ATOP);
                        view.invalidate();
                        break;
                    }

                    case MotionEvent.ACTION_UP:
                        v.performClick();

                    case MotionEvent.ACTION_CANCEL: {
                        ImageView view = (ImageView) v;

                        //Clear the overlay
                        view.getDrawable().clearColorFilter();
                        view.invalidate();
                        break;
                    }
                }

                return true;
            }
        };
    }

    ...
}

Luego lo uso con onTouchListener:

ImageView img=(ImageView) view.findViewById(R.id.image);
img.setOnClickListener(new View.OnClickListener() {
    @Override
    public void onClick(View v) { /* Your click action */ }
});
img_zc.setOnTouchListener(Utility.imgPress()); //Or Utility.imgPress(int_color_with_alpha)

Es muy simple si tiene muchas imágenes y desea un efecto onTouch simple, sin ningún elemento de diseño XML y solo una imagen.

neoteknic
fuente
3

Creo que ImageButton es una mejor solución

<ImageButton
    android:layout_width="96dp"
    android:layout_height="56dp"
    android:src="@mipmap/ic_launcher"
    android:adjustViewBounds="true"
    android:background="@android:color/transparent"
    android:foreground="@drawable/selector" />
Dan Alboteanu
fuente
2

Tengo una solución más bella si usa imágenes de fondo :)

public static void blackButton(View button){
    button.setOnTouchListener(new OnTouchListener() {

        public boolean onTouch(View v, MotionEvent event) {
            switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN: {
                    v.getBackground().setColorFilter(0xf0f47521,PorterDuff.Mode.SRC_ATOP);
                    v.invalidate();
                    break;
                }
                case MotionEvent.ACTION_UP: {
                    v.getBackground().clearColorFilter();
                    v.invalidate();
                    break;
                }
            }
            return false;
        }
    });
}
András
fuente
2

O:

Puede utilizar este formulario, con el botón de imagen.

Crear archivo res/drawable/btn_video.xml:

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

Y res/layout/activity_main.xml:

<ImageButton
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:id="@+id/imageButton"
    android:layout_gravity="center_horizontal"
    android:onClick="eventImageBtn"
    android:background="@drawable/btn_video"
    android:adjustViewBounds="true"
    android:scaleType="fitXY"
/>

Su imagen cambia con un clic y puede ajustar con un diseño lineal:

<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:fillViewport="true">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        android:background="@color/menu_item_background">

        <LinearLayout android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical"
                      android:paddingLeft="@dimen/main_screen_side_padding" android:paddingRight="@dimen/main_screen_side_padding" android:paddingTop="@dimen/main_screen_side_padding" android:paddingBottom="@dimen/main_screen_side_padding"
                      android:background="#ffb3ff13" android:weightSum="10.00">


            <LinearLayout android:layout_weight="2.50" android:background="#ff56cfcd" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="0dp" >

                <ImageButton
                    android:layout_width="match_parent"
                    android:layout_height="match_parent"
                    android:id="@+id/imageButton"
                    android:layout_gravity="center_horizontal"
                    android:onClick="eventImageBtn"
                    android:background="@drawable/btn_video"
                    android:adjustViewBounds="true"
                    android:scaleType="fitXY"
                />
            </LinearLayout>

            <LinearLayout android:layout_weight="0.50" android:layout_height="0dp" android:background="#ffffffff" android:orientation="vertical" android:layout_width="fill_parent" >
            </LinearLayout>

            <LinearLayout android:layout_weight="4.50" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="0dp" android:background="#ff8aa5ff">
            </LinearLayout>

            <LinearLayout android:layout_weight="0.50" android:layout_height="0dp" android:background="#ffffffff" android:orientation="vertical" android:layout_width="fill_parent" >
            </LinearLayout>

            <LinearLayout android:layout_weight="2.00" android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="0dp" android:background="#ffff7d1a" >
            </LinearLayout>

        </LinearLayout>
    </LinearLayout>
</ScrollView>
Alex Zaraos
fuente
2

Aquí está mi solución, que, utilizando la biblioteca " nineOldAndroids ", también admite API antiguas:

rootView.setOnTouchListener(new OnTouchListener() {

    @Override
    public boolean onTouch(final View v, final MotionEvent event) {

        switch (event.getAction()) {

            case MotionEvent.ACTION_UP:
            case MotionEvent.ACTION_CANCEL:
                v.setBackgroundResource(R.drawable.listview_normal);
                ViewHelper.setAlpha(imageView, 1);
                break;

            case MotionEvent.ACTION_DOWN:
                v.setBackgroundResource(0);
                v.setBackgroundColor(getResources().getColor(R.color.listview_pressed));
                ViewHelper.setAlpha(imageView, 0.75f);
                break;
        }
        return false;
    }
});

Asume que rootView es la celda en sí (el diseño), y que tiene un único imageView que desea que se vea afectado por el color que desea aplicar a toda la celda.


EDITAR: si lo desea, también puede extender ImageView para manejar el primer plano y configurarlo en "? Android: attr / selectableItemBackground". Hay una biblioteca para esto aquí y un tutorial sobre cómo hacerlo para cualquier vista que desee, aquí .

desarrollador de Android
fuente
@madlymad gracias por arreglar el formato del código, aunque creo que algo salió mal con la sangría. De todos modos, es lo suficientemente bueno como para poder leerlo ...
desarrollador de Android
1

Gracias por la ayuda en este hilo. Sin embargo, te perdiste una cosa ... también debes manejar ACTION_CANCEL. Si no lo hace, es posible que no restaure correctamente el valor alfa de ImageView en caso de que una vista principal en la jerarquía de vistas intercepte un evento táctil (piense en un ScrollView que envuelve su ImageView).

Aquí hay una clase completa que se basa en la clase anterior, pero también se ocupa de ACTION_CANCEL. Utiliza una clase auxiliar ImageViewCompat para abstraer las diferencias en la API de JellyBean pre-post.

public class ChangeAlphaOnPressedTouchListener implements OnTouchListener {

    private final float pressedAlpha;

    public ChangeAlphaOnPressedTouchListener(float pressedAlpha) {
        this.pressedAlpha = pressedAlpha;
    }

    @Override
    public boolean onTouch(View v, MotionEvent event) {
        ImageView iv = (ImageView) v;
        switch (event.getAction()) {
        case MotionEvent.ACTION_DOWN:
            ImageViewCompat.setAlpha(iv, pressedAlpha);
            break;

        case MotionEvent.ACTION_MOVE:
            if (isInsideViewBounds(v, event)) {
                ImageViewCompat.setAlpha(iv, pressedAlpha);
            } else {
                ImageViewCompat.setAlpha(iv, 1f);
            }
            break;
        case MotionEvent.ACTION_UP:
            ImageViewCompat.setAlpha(iv, 1f);
            break;
        case MotionEvent.ACTION_CANCEL:
            ImageViewCompat.setAlpha(iv, 1f);
        }
        return false;
    }

    private static boolean isInsideViewBounds(View v, MotionEvent event) {
        return event.getX() > 0 && event.getX() < v.getWidth() && event.getY() > 0
                && event.getY() < v.getHeight();
    }
}
Matt Accola
fuente
1

Aquí está mi código. La idea es que ImageView obtiene un filtro de color cuando el usuario lo toca y el filtro de color se elimina cuando el usuario deja de tocarlo.

Martin Booka Weser, András, Ah Lam, altosh, la solución no funciona cuando ImageView también tiene onClickEvent. La solución worawee.s y kcoppock (con ImageButton) requiere un fondo, lo que no tiene sentido cuando ImageView no es transparente.

Esta es una extensión de la idea AZ_ sobre el filtro de color.

class PressedEffectStateListDrawable extends StateListDrawable {

    private int selectionColor;

    public PressedEffectStateListDrawable(Drawable drawable, int selectionColor) {
        super();
        this.selectionColor = selectionColor;
        addState(new int[] { android.R.attr.state_pressed }, drawable);
        addState(new int[] {}, drawable);
    }

    @Override
    protected boolean onStateChange(int[] states) {
        boolean isStatePressedInArray = false;
        for (int state : states) {
            if (state == android.R.attr.state_pressed) {
                isStatePressedInArray = true;
            }
        }
        if (isStatePressedInArray) {
            super.setColorFilter(selectionColor, PorterDuff.Mode.MULTIPLY);
        } else {
            super.clearColorFilter();
        }
        return super.onStateChange(states);
    }

    @Override
    public boolean isStateful() {
        return true;
    }
}

uso:

Drawable drawable = new FastBitmapDrawable(bm);
imageView.setImageDrawable(new PressedEffectStateListDrawable(drawable, 0xFF33b5e5));
Malachiasz
fuente
1

Lo intenté con:

<ImageButton
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:contentDescription="@string/get_started"
        android:src="@drawable/home_started"
        style="?android:borderlessButtonStyle"
        android:adjustViewBounds="true"
        android:clickable="true"
        android:elevation="5dp"
        android:longClickable="true" />

y esto funcionó. Tenga en cuenta en la línea:style="?android:borderlessButtonStyle"

aviit
fuente
Esto no funciona en el caso de relleno 0 y la imagen ocupa toda el área de la vista.
desarrollador de Android
1

Creo que la forma más sencilla es crear un nuevo archivo XML. En este caso, llamémoslo "ejemplo.xml" en la carpeta dibujable y coloquemos el siguiente código:

<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:drawable="@color/blue"
          android:state_pressed="true" />

</selector>

Pero antes de eso, debe configurar los colores en el archivo colors.xml, en la carpeta de valores, así:

<resources>
    <color name="blue">#0000FF</color>
</resources>

Hecho eso, simplemente configura el Botón / ImageButton para usar el nuevo diseño, así:

<ImageView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:background="@drawable/example"
/>

Luego, cuando haga clic en esa imagen, cambiará al color establecido en

<item android:drawable="@color/blue"
      android:state_pressed="true" />

dando la retroalimentación que desea ...

Lima Neto
fuente
1

Esta es la mejor solución que he visto. Es más genérico.

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

    <alpha
        android:duration="100"
        android:fromAlpha="0.0"
        android:interpolator="@android:anim/accelerate_interpolator"
        android:toAlpha="1.0" />
</set>
Nilesh
fuente
2
¿En qué lugar y archivo se debe inyectar?
DmitryBoyko
0

Hice lo siguiente en XML, con 0 relleno alrededor de la imagen y ondulación en la parte superior de la imagen:

<ImageView
    android:layout_width="100dp"
    android:layout_height="100dp"
    android:background="@drawable/my_image"
    android:clickable="true"
    android:focusable="true"
    android:src="?android:attr/selectableItemBackground" />
Alguien en alguna parte
fuente
-1

Por ahora, deberíamos desarrollar la práctica del Diseño de Materiales . En este caso, podría agregar un efecto dominó en un ImageView.

desbordamiento
fuente
-1

Simplemente agregue el atributo XML, android: clickable = "true" ...

Sandipkumar Savani
fuente