Come posso dare a un clic di visualizzazione immagine l'effetto come un pulsante su Android?


84

Ho imageview nella mia app Android che sto usando come un pulsante con l'evento onClick dato, ma come puoi immaginare non dà a imageview un effetto cliccabile quando cliccato. Come posso ottenerlo?

Risposte:


53

È possibile progettare immagini diverse per gli stati cliccato / non cliccato e impostarle in onTouchListener come segue

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 scelta migliore è definire un selettore come segue

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

e seleziona l'immagine nell'evento:

v.setOnTouchListener(new OnTouchListener() {
            @Override
            public boolean onTouch(View arg0, MotionEvent arg1) {
                v.setSelected(arg1.getAction()==MotionEvent.ACTION_DOWN);
                return true;
            }
        });

1
puoi spiegare cosa res.getDrawable res cosa fa?
VenushkaT

v.setSelected == true una sola volta, passando immediatamente a false a causa di MotionEvent.ACTION_MOVE. Una volta rilasciato il dito, si verifica MotionEvent.ACTION_UP. Se si utilizza il metodo selector, utilizzare una logica separata per setSelected o setPressed. if (arg1.getAction () == MotionEvent.ACTION_DOWN) {v.setPressed (true); } else if (arg1.getAction () == MotionEvent.ACTION_UP) {v.setPressed (false); }
Adam Denoon

È meglio MotionEvent.ACTION_DOWN || MotionEvent.ACTION_MOVEmantenere l'immagine visibile finché stiamo premendo.
Alaa M.

Non ne hai bisogno setOnTouchListener(.... Puoi semplicemente creare <selector ...>e quindi impostare ImageView cliccabile in XML come<ImageView ... android:clickable="true" android:focusable="true" android:src="@drawable/my_selector" />
Pierre

76

Puoi farlo con una singola immagine usando qualcosa del genere:

     //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;
        }
    });

Probabilmente lo trasformerò in una sottoclasse di ImageView (o ImageButton in quanto è anche una sottoclasse di ImageView) per una più facile riutilizzabilità, ma questo dovrebbe consentire di applicare un aspetto "selezionato" a un'immagine.


2
Ho anche aggiunto una custodia per ACTION_CANCEL, funziona benissimo, grazie!
Alan

Buona chiamata: l'avevo aggiunto io stesso nel mio codice, ma lo aggiornerò anche qui.
Mr Zorn

1
Questa potrebbe essere un'altra domanda, ma come posso annullare dopo ACTION_UP? Nello specifico ... L'utente colpisce l'immagine. L'utente trascina il dito fuori dall'immagine per annullarla. Ma l'azione non viene annullata con questo codice
sudocoder

Aggiungerò anche MotionEvent.ACTION_OUTSIDE;)
bonnyz

3
potresti voler tornare false, altrimenti l' onClick()evento effettivo della visualizzazione non verrà attivato
Nimrod Dayan,

45

È possibile fare con un solo file immagine utilizzando il metodo ColorFilter. Tuttavia, ColorFilter si aspetta di lavorare con ImageViews e non con i pulsanti, quindi devi trasformare i tuoi pulsanti in ImageViews. Questo non è un problema se stai comunque usando le immagini come pulsanti, ma è più fastidioso se hai del testo ... Comunque, supponendo che tu trovi un modo per aggirare il problema con il testo, ecco il codice da usare:

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

Ciò applica una sovrapposizione rossa al pulsante (il codice colore è il codice esadecimale per il rosso completamente opaco - le prime due cifre sono trasparenti, quindi è RR GG BB.).


3
Potresti spiegare cosa accadrà dopo che il codice è stato eseguito e dove dovrebbe essere chiamato? Ho provato a chiamare queste 2 linee sull'inizializzazione di imageView: dipinge la mia immagine in rosso e non succede nulla, né al clic, né al tocco. Lo stesso quando si chiama al tocco.
esteewhy

45

EDIT : Sebbene la risposta originale di seguito funzioni ed è facile da configurare, fare riferimento a questo post di un Android Developer Advocate di Google se si desidera / è necessaria un'implementazione più efficiente. Si noti inoltre che l' android:foregroundattributo arriva a tutte le visualizzazioni , incluso ImageView, per impostazione predefinita in Android M.


Il problema con l'utilizzo di un selettore per un ImageView è che puoi solo impostarlo come sfondo della vista: finché l'immagine è opaca, non vedrai l'effetto del selettore dietro di essa.

Il trucco è racchiudere il tuo ImageView in un FrameLayout con l'attributo android:foregroundche ci permette di definire una sovrapposizione per il suo contenuto. Se impostiamo android:foregroundun selettore (ad es. ?android:attr/selectableItemBackgroundPer il livello API 11+) e OnClickListenercolleghiamo al FrameLayout invece che a ImageView, l'immagine verrà sovrapposta al disegnabile del nostro selettore - l'effetto clic che desideriamo!

Ecco:

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

(Nota che questo dovrebbe essere inserito nel layout genitore.)

final View imageButton = findViewById(R.id.imageButton);
imageButton.setOnClickListener(new OnClickListener(){
    @Override
    public void onClick(View view) {
        // do whatever we wish!
    }
});

2
Grande ! Questa è un'ottima soluzione. Stessa soluzione utilizzata nell'applicazione Contatti per SMS o azioni di chiamata.
Jerry

Non funziona con API <11.? Android: attr / selectableItemBackground richiede il livello API 11 (il minimo attuale è 8)
MSaudi

L' selectableItemBackgroundattributo è stato aggiunto solo nel livello API 11, quindi è necessario utilizzare un altro selettore se si desidera utilizzare questa soluzione per i livelli API precedenti. Ad esempio, per una delle mie applicazioni che supporta il livello API 7, utilizzo la @drawable/list_selector_holo_lightrisorsa generata utilizzando lo strumento Android Holo Colors Generator .
justasm

Puoi ottenere lo stesso comportamento usando solo 1 <ImageButton>con selectableItemBackground!
Yohan Dahmani

28

Usa style = "? Android: borderlessButtonStyle" nel file XML. Mostrerà l'effetto clic predefinito di Android.

<ImageView
    android:id="@+id/imageView1"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_launcher" 
    style="?android:borderlessButtonStyle"
/>

1
Questa è in realtà la risposta migliore,
MOLTO

1
Questo imposta il padding, e anche se imposti il ​​padding su 0, se l'immagine che gli dai occupa l'intera imageView, non vedrai alcun effetto del clic.
sviluppatore Android

2
@androiddeveloper usa android:adjustViewBounds="true"per annullare il riempimento.
Hafez Divandari

1
Si consiglia di utilizzare style="?android:attr/borderlessButtonStyle": developer.android.com/guide/topics/ui/controls/…
Hafez Divandari

Utilizzare style="?android:actionButtonStyle"per un ImageView selezionabile su una ActionBar o ToolBar.
palindrom

21

Usa semplicemente un ImageButton .


3
Personalmente non riesco a farlo sembrare ImageView. Nessun bordo, allunga l'immagine alla dimensione di ImageButton ecc. Se puoi dare questo problema di bordo e allungamento, e aggiorna il tuo post. La mia reputazione va a te come taglia =)
tottenuta il

15

Ecco il mio modo semplice per risolverlo:

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);
    });

Nel file 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>

Ottima soluzione - grazie! Ho sfogliato questo post provando tutti quelli concisi - e senza successo. Finalmente sono arrivato qui e ha funzionato per me. Un'osservazione: se hai 2 o più pulsanti a cui vuoi applicare l'animazione ... per il mio codice, ho scoperto che ho bisogno di creare un'istanza univoca dell'oggetto Animation per ogni pulsante a cui volevo applicare l'effetto. Il riutilizzo della stessa istanza causava lo sfarfallio di tutti i pulsanti quando si faceva clic su 1.
Gene Bo

9

Imposta lo sfondo selezionabile su ImageView e aggiungi un po 'di riempimento. Quindi allegare il file 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"/>

C'è un modo per usarlo senza impostare il riempimento e fare in modo che l'intera ImageView abbia l'effetto e non solo l'area vuota?
sviluppatore Android

Questo mostrerà l'ondulazione in cubi, abbiamo bisogno dell'ondulazione centrale
Kishan Solanki

8

Per definire la scelta disegnabile del selettore

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

Devo usare android: state_pressed invece di 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>

6

Se vuoi ondeggiare quando viene toccato, può essere dato da questo codice:

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

Allo stesso modo, puoi implementare l'effetto clic per TextView

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

5

Puoi provare con android:background="@android:drawable/list_selector_background" per ottenere lo stesso effetto di "Aggiungi sveglia" nella "Sveglia" predefinita (ora Orologio da tavolo).


4

Questo ha funzionato per me:

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;
            }

        });

@Edit: come ha detto Gunhan, ci sarà un problema di compatibilità con le versioni precedenti con il metodo setImageAlpha. Ho usato questo metodo:

public static void setImageAlpha(ImageView img, int alpha)
    {
        if(Build.VERSION.SDK_INT > 15)
        {
            img.setImageAlpha(alpha);
        }
        else
        {
            img.setAlpha(alpha);
        }
    }

1
setImageAlpha richiede il livello API 16. Pertanto, per app retrocompatibili non è possibile utilizzarlo
Gunhan

1
@Gunhan in realtà, puoi utilizzare la libreria "nineOldAndroids" che consente di utilizzare alpha anche su API meno recenti. basta usare: ViewHelper.setAlpha (view, alpha);
sviluppatore Android

4

Faccio alcune cose simili Vedi adatto a te o no

Visualizza Press Effect Helper:

  • utilizzo: esegui alcuni semplici effetti di stampa come iOS

    Utilizzo semplice:

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

  • ViewPressEffectHelper.attach (img)

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


4

In combinazione con tutte le risposte precedenti, volevo che ImageView venisse premuto e cambiasse stato, ma se l'utente si spostava, "annulla" e non esegue un onClickListener.

Ho finito per creare un oggetto Point all'interno della classe e impostare le sue coordinate in base a quando l'utente ha premuto su ImageView. Su MotionEvent.ACTION_UP ho registrato un nuovo punto e ho confrontato i punti.

Posso solo spiegarlo così bene, ma ecco cosa ho fatto.

// 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;
    }
});

Ho un onClickListener impostato su imageView, ma questo può essere un metodo.


aggiungendo case MotionEvent.ACTION_CANCELcon la stessa funzionalità di MotionEvent.ACTION_UPallora è possibile "svuotare" la vista se l'utente esegue un "trascinamento" che non è un'azione di clic.
madlymad

4

Puoi eseguire l'override setPressedin ImageView e filtrare i colori lì, invece di creare listener 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();
    }
}

4

Sulla base della risposta del signor Zorn , utilizzo un metodo statico nella mia classe di utilità astratta:

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;
            }
        };
    }

    ...
}

Quindi 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)

È molto semplice se si hanno molte immagini e si desidera un semplice effetto onTouch, senza alcun disegno XML e una sola immagine.




3

Penso che ImageButton sia una soluzione migliore

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

2

Ho una soluzione più bella se usi immagini di sfondo :)

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;
        }
    });
}

2

O:

Puoi usare questo modulo, con il pulsante immagine.

Crea file 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>

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

La tua immagine cambia con un clic e puoi regolarla con un layout lineare:

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

2

Ecco la mia soluzione, che, utilizzando la libreria " nineOldAndroids ", supporta anche le vecchie API:

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;
    }
});

Presume che rootView sia la cella stessa (il layout) e che abbia una singola imageView che desideri sia influenzata dal colore che desideri applicare all'intera cella.


EDIT: se lo desideri, puoi anche estendere ImageView per gestire il primo piano e impostarlo su "? Android: attr / selectableItemBackground". C'è una libreria per questo qui e un tutorial su come farlo per qualsiasi visualizzazione desideri, qui .


@madlymad grazie per aver corretto la formattazione del codice, anche se penso che qualcosa sia andato storto con il rientro. Ad ogni modo, è abbastanza buono da poterlo leggere ...
sviluppatore Android

1

Grazie per l'aiuto su questo thread. Tuttavia, ti sei perso una cosa ... devi gestire anche ACTION_CANCEL. Se non lo fai, potresti non ripristinare correttamente il valore alfa di ImageView nel caso in cui una vista principale nella gerarchia della vista intercetti un evento di tocco (pensa a ScrollView che avvolge ImageView).

Ecco una classe completa che si basa sulla classe precedente ma si occupa anche di ACTION_CANCEL. Utilizza una classe helper ImageViewCompat per astrarre le differenze nell'API 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();
    }
}

1

Ecco il mio codice. L'idea è che ImageView ottenga il filtro del colore quando l'utente lo tocca e il filtro del colore viene rimosso quando l'utente smette di toccarlo.

Martin Booka Weser, András, Ah Lam, altosh, la soluzione non funziona quando ImageView ha anche onClickEvent. La soluzione worawee.s e kcoppock (con ImageButton) richiede uno sfondo, che non ha senso quando ImageView non è trasparente.

Questa è l'estensione dell'idea AZ_ sul filtro colore.

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;
    }
}

utilizzo:

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

1

Ho provato 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" />

e questo ha funzionato. Si prega di notare sulla linea:style="?android:borderlessButtonStyle"


Questo non funziona nel caso di riempimento 0 e l'immagine occupa l'intera area della vista.
sviluppatore Android

1

Penso che il modo più semplice sia creare un nuovo file XML. In questo caso, chiamiamolo "example.xml" nella cartella drawable e inseriamo il seguente codice:

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

</selector>

Ma prima devi impostare i colori nel file colors.xml, nella cartella dei valori, in questo modo:

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

Ciò fatto, è sufficiente impostare il pulsante / pulsante immagine per utilizzare il nuovo layout, in questo modo:

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

Quindi, quando fai clic su quell'immagine, cambierà nel colore impostato in

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

dando il feedback che desideri ...


1

Questa è la migliore soluzione che abbia mai visto. È più generico.

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

2
In quale luogo e file dovrebbe essere iniettato?
DmitryBoyko

0

Ho fatto quanto segue in XML, con 0 riempimento intorno all'immagine e increspatura sopra l'immagine:

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


Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.