Ostrzeżenie onTouchListener: onTouch powinien wywołać View # performClick po wykryciu kliknięcia


110

Stworzyłem onTouchListener. Niestety onTouch () wyświetla throwsmi ostrzeżenie:

com/calculator/activitys/Calculator$1#onTouch should call View#performClick when a click is detected

Co to znaczy? Nie znalazłem żadnych informacji o tym ostrzeżeniu. Oto pełny kod:

LinearLayout llCalculatorContent = (LinearLayout) fragmentView.findViewById(R.id.calculator_content);

llCalculatorContent.setOnTouchListener(new View.OnTouchListener() {

    @Override
    public boolean onTouch(View v, MotionEvent event) {
        Tools.hideKeyboard(getActivity(), getView());
        getView().clearFocus();
        return false;
    }   
});

17
chcesz pozbyć się ostrzeżenia po prostu zadzwoń v.performClick(). Implementacja zagra trochę dźwięku (jeśli masz ją włączoną na swoim urządzeniu) i wywoła onClickListener, którego prawdopodobnie nie przesłoniłeś
Blackbelt

Twoja odpowiedź była poprawna. Dziękuję
Trzy Gracje

Odpowiedzi:


131

Proszę bardzo:

public boolean onTouch(View v, MotionEvent event) {
    switch (event.getAction()) {
    case MotionEvent.ACTION_DOWN:
        //some code....
        break;
    case MotionEvent.ACTION_UP:
        v.performClick();
        break;
    default:
        break;
    }
    return true;
}

14
czy nie powinno być wywoływane tylko wtedy, gdy zdarzenie == MotionEvent.Action_UP, czy coś takiego? Poza tym, czy zwrócenie „false” nie wywoła oryginalnej metody klikania, więc zamiast tego powinno się zwrócić „true”?
programista androidów

@longilong Cóż, jeśli chcesz, możesz również ustawić go tak, aby używał przełącznika, ale to logicznie to samo ...
programista Androida

3
Mam podobne ostrzeżenie. Ale mój scenariusz jest trochę inny, ponieważ ustawiam anonimowy OnTouchListener podczas konfigurowania RecyclerView (wywołując myRecyclerView.setOnTouchListener. Android Studio oznacza całą anonimową klasę z podobnym ostrzeżeniem i nawet jeśli dodam v.performClick, ostrzeżenie pozostaje.
fr4gus

8
jeśli zwrócimy false z tej metody, nie powinniśmy być zobowiązani do wywołania performClick, prawda? W tym przypadku nie rozumiem, dlaczego ostrzeżenie o
kłaczkach

9
Nie robi nic, aby naprawić ostrzeżenie.
TheLibrarian,

2

Możesz powstrzymać Lint

@SuppressLint("ClickableViewAccessibility")

Powinieneś zadzwonić do performClick()środka onTouchEvent().

@Override
public boolean onTouchEvent(MotionEvent event) {
    //A logic 

    performClick();
    return super.onTouchEvent(event);
}

lub

findViewById(R.id.view1).setOnTouchListener(new View.OnTouchListener() {
    @Override
    public boolean onTouch(View v, MotionEvent event) {

        v.performClick();

        return v.onTouchEvent(event);
    }
});

OnTouch pływ

Przeczytaj więcej tutaj


1
Nie musisz przesłonić performClick().
Udostępnij

1

W przypadku, gdy nie używasz, Custom Viewktóre jawnie zastępuje onPerformClick, ostrzeżenie nie zostanie usunięte po prostu podążając za odpowiedzią Secko.

Oprócz jego odpowiedzi, aby zrobić to samo na klasach takich jak android.widget.Buttonlub Button, musisz stworzyć prosty niestandardowy widok, który rozszerzy widok docelowy.

Przykład:

Klasa widoku niestandardowego:

public class UselessButton extends AppCompatButton {
    public UselessButton(Context context) {
        super(context);
    }

    public UselessButton(Context context, AttributeSet attrs) {
        super(context, attrs);
    }

    public UselessButton(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }

    @Override
    public boolean performClick() {
        return super.performClick();
    }
}

XML :

<stackoverflow.onEarth.UselessButton
    android:id="@+id/left"
    android:layout_width="60dp"
    android:layout_height="60dp"
    android:layout_marginStart="16dp"
    android:layout_marginTop="16dp"
    android:layout_marginEnd="8dp"
    android:layout_marginBottom="8dp"
    android:background="@drawable/left"
    app:layout_constraintBottom_toBottomOf="parent"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintHorizontal_bias="0.16"
    app:layout_constraintStart_toStartOf="parent"
    app:layout_constraintTop_toTopOf="parent"
    app:layout_constraintBaseline_toBaselineOf="@+id/right"
    app:layout_constraintVertical_bias="0.5" />

Java :

    left.setOnTouchListener((v, event) -> {
        if (event.getAction() == MotionEvent.ACTION_DOWN) {
            enLeft = 1;
            enRight = 0;
            return true;
        } else if (event.getAction() == MotionEvent.ACTION_UP) {
            enLeft = 0;
            v.performClick();
            return false;
        } else {
            return false;
        }
    });

Bieżące problemy: ostrzeżenie zostaje rozwiązane przez IDE, ale nie widzę tego praktycznie wykonującego kliknięcie na prawdziwym urządzeniu z Androidem.

EDYCJA : Naprawiono zdarzenie kliknięcia: UżyjView.setPressed(boolean)

down.setOnTouchListener((v, event) -> {
    if (event.getAction() == MotionEvent.ACTION_DOWN) {
        enFront = 0;
        enBack = 1;
        left.setPressed(true);
        return true;
    } else if (event.getAction() == MotionEvent.ACTION_UP) {
        enBack = 0;
        v.performClick();
        v.setPressed(false);
        return false;
    } else {
        return false;
    }

0

po prostu wywołaj metodę performClick, na przykład:

@Override
public boolean onTouch(View v, MotionEvent event) {
    v.performClick();
    Tools.hideKeyboard(getActivity(), getView());
    getView().clearFocus();
    return false;
}   

0

Miałem podobny problem z a MultiTouchListeneri rozwiązałem go, implementując a GestureDetectori nasłuchując a SingleTap(To nie usuwa ostrzeżenia, ale zaczyna wyzwalać onClickzdarzenia w moim widoku)

class TouchListener(context: Context) : MultiTouchListener() {

    private var tochedView: View? = null
    private var mGestureDetector = CustomGestureDetector()
    private var gestureDetector: GestureDetector = GestureDetector(context, mGestureDetector)

    @SuppressLint("ClickableViewAccessibility")
    override fun onTouch(view: View?, event: MotionEvent?): Boolean {
        val aux = super.onTouch(view, event)

        tochedView = view
        gestureDetector.onTouchEvent(event)

        return aux
    }

    private inner class CustomGestureDetector: GestureDetector.SimpleOnGestureListener() {

        override fun onSingleTapUp(e: MotionEvent?): Boolean {
            // this will be called even when a double tap is
            tochedView?.performClick()
            return super.onSingleTapUp(e)
        }

        override fun onSingleTapConfirmed(e: MotionEvent?): Boolean {
            // this will only be called after the detector is confident that the
            // user's first tap is not followed by a second tap leading to a double-tap gesture.
            tochedView?.performClick()
            return super.onSingleTapConfirmed(e)
        }

    }

}
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.