Saya memiliki EditText
pandangan di android. Dalam hal ini saya ingin mendeteksi gesekan ke kiri atau kanan. Saya bisa mendapatkannya di ruang kosong menggunakan kode di bawah ini. Namun ini tidak berfungsi saat saya menggesek file EditText
. Bagaimana aku melakukan itu? Tolong beritahu saya jika saya melakukan sesuatu yang salah. Terima kasih.
Kode yang Digunakan:
switch (touchevent.getAction())
{
case MotionEvent.ACTION_DOWN:
{
oldTouchValue = touchevent.getX();
break;
}
case MotionEvent.ACTION_UP:
{
float currentX = touchevent.getX();
if (oldTouchValue < currentX)
{
// swiped left
}
if (oldTouchValue > currentX )
{
swiped right
}
break;
}
}
Jawaban:
Detektor gesekan kiri ke kanan paling sederhana:
Di kelas aktivitas Anda, tambahkan atribut berikut:
private float x1,x2; static final int MIN_DISTANCE = 150;
dan
onTouchEvent()
metode timpa :@Override public boolean onTouchEvent(MotionEvent event) { switch(event.getAction()) { case MotionEvent.ACTION_DOWN: x1 = event.getX(); break; case MotionEvent.ACTION_UP: x2 = event.getX(); float deltaX = x2 - x1; if (Math.abs(deltaX) > MIN_DISTANCE) { Toast.makeText(this, "left2right swipe", Toast.LENGTH_SHORT).show (); } else { // consider as something else - a screen tap for example } break; } return super.onTouchEvent(event); }
sumber
getAction()
mengembalikan data campuran dari kedua tipe tindakan dan indeks penunjuk, tidak akan lebih baik untuk digunakangetActionMasked()
, yang hanya mengembalikan tipe tindakan?Saya suka kode dari @ user2999943. Tetapi hanya beberapa perubahan kecil untuk tujuan saya sendiri.
@Override public boolean onTouchEvent(MotionEvent event) { switch(event.getAction()) { case MotionEvent.ACTION_DOWN: x1 = event.getX(); break; case MotionEvent.ACTION_UP: x2 = event.getX(); float deltaX = x2 - x1; if (Math.abs(deltaX) > MIN_DISTANCE) { // Left to Right swipe action if (x2 > x1) { Toast.makeText(this, "Left to Right swipe [Next]", Toast.LENGTH_SHORT).show (); } // Right to left swipe action else { Toast.makeText(this, "Right to Left swipe [Previous]", Toast.LENGTH_SHORT).show (); } } else { // consider as something else - a screen tap for example } break; } return super.onTouchEvent(event); }
sumber
Ini adalah kelas lucu yang saya gunakan (dalam kasus saya ingin menangkap acara di View, jika itu adalah ViewGroup, saya menggunakan implementasi kedua):
import android.util.Log; import android.view.MotionEvent; import android.view.View; public class SwipeDetector implements View.OnTouchListener{ private int min_distance = 100; private float downX, downY, upX, upY; private View v; private onSwipeEvent swipeEventListener; public SwipeDetector(View v){ this.v=v; v.setOnTouchListener(this); } public void setOnSwipeListener(onSwipeEvent listener) { try{ swipeEventListener=listener; } catch(ClassCastException e) { Log.e("ClassCastException","please pass SwipeDetector.onSwipeEvent Interface instance",e); } } public void onRightToLeftSwipe(){ if(swipeEventListener!=null) swipeEventListener.SwipeEventDetected(v,SwipeTypeEnum.RIGHT_TO_LEFT); else Log.e("SwipeDetector error","please pass SwipeDetector.onSwipeEvent Interface instance"); } public void onLeftToRightSwipe(){ if(swipeEventListener!=null) swipeEventListener.SwipeEventDetected(v,SwipeTypeEnum.LEFT_TO_RIGHT); else Log.e("SwipeDetector error","please pass SwipeDetector.onSwipeEvent Interface instance"); } public void onTopToBottomSwipe(){ if(swipeEventListener!=null) swipeEventListener.SwipeEventDetected(v,SwipeTypeEnum.TOP_TO_BOTTOM); else Log.e("SwipeDetector error","please pass SwipeDetector.onSwipeEvent Interface instance"); } public void onBottomToTopSwipe(){ if(swipeEventListener!=null) swipeEventListener.SwipeEventDetected(v,SwipeTypeEnum.BOTTOM_TO_TOP); else Log.e("SwipeDetector error","please pass SwipeDetector.onSwipeEvent Interface instance"); } public boolean onTouch(View v, MotionEvent event) { switch(event.getAction()){ case MotionEvent.ACTION_DOWN: { downX = event.getX(); downY = event.getY(); return true; } case MotionEvent.ACTION_UP: { upX = event.getX(); upY = event.getY(); float deltaX = downX - upX; float deltaY = downY - upY; //HORIZONTAL SCROLL if(Math.abs(deltaX) > Math.abs(deltaY)) { if(Math.abs(deltaX) > min_distance){ // left or right if(deltaX < 0) { this.onLeftToRightSwipe(); return true; } if(deltaX > 0) { this.onRightToLeftSwipe(); return true; } } else { //not long enough swipe... return false; } } //VERTICAL SCROLL else { if(Math.abs(deltaY) > min_distance){ // top or down if(deltaY < 0) { this.onTopToBottomSwipe(); return true; } if(deltaY > 0) { this.onBottomToTopSwipe(); return true; } } else { //not long enough swipe... return false; } } return true; } } return false; } public interface onSwipeEvent { public void SwipeEventDetected(View v, SwipeTypeEnum SwipeType); } public SwipeDetector setMinDistanceInPixels(int min_distance) { this.min_distance=min_distance; return this; } public enum SwipeTypeEnum { RIGHT_TO_LEFT,LEFT_TO_RIGHT,TOP_TO_BOTTOM,BOTTOM_TO_TOP } }
dan ini adalah contoh penggunaan:
filters_container=(RelativeLayout)root.findViewById(R.id.filters_container); new SwipeDetector(filters_container).setOnSwipeListener(new SwipeDetector.onSwipeEvent() { @Override public void SwipeEventDetected(View v, SwipeDetector.SwipeTypeEnum swipeType) { if(swipeType==SwipeDetector.SwipeTypeEnum.LEFT_TO_RIGHT) getActivity().onBackPressed(); } });
Dalam beberapa kasus, Anda ingin mendeteksi gerakan menggesek pada wadah dan meneruskan Peristiwa sentuh kepada anak-anak sehingga Anda dapat membuat grup Tampilan Kustom, katakanlah RelativeLayout dan timpa onInterceptTouchEvent, dan di sana Anda dapat mendeteksi peristiwa gesekan tanpa memblokir izin Peristiwa Sentuh untuk tampilan anak Anda, misalnya:
import android.content.Context; import android.util.AttributeSet; import android.view.MotionEvent; import android.widget.RelativeLayout; public class SwipeDetectRelativeLayout extends RelativeLayout { private float x1,x2; static final int MIN_DISTANCE=150; private onSwipeEventDetected mSwipeDetectedListener; public SwipeDetectRelativeLayout(Context context) { super(context); } public SwipeDetectRelativeLayout(Context context, AttributeSet attrs) { super(context, attrs); } public SwipeDetectRelativeLayout(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } @Override public boolean onInterceptTouchEvent(MotionEvent ev) { switch(ev.getAction()) { case MotionEvent.ACTION_DOWN: x1 = ev.getX(); break; case MotionEvent.ACTION_UP: x2 = ev.getX(); float deltaX = x2 - x1; if (Math.abs(deltaX) > MIN_DISTANCE) { //swiping right to left if(deltaX<0) { if(mSwipeDetectedListener!=null) mSwipeDetectedListener.swipeEventDetected(); } } break; } return super.onInterceptTouchEvent(ev); } public interface onSwipeEventDetected { public void swipeEventDetected(); } public void registerToSwipeEvents(onSwipeEventDetected listener) { this.mSwipeDetectedListener=listener; } }
sumber
Peristiwa gesek adalah sejenis
onTouch
acara. Cukup sederhanakan jawaban @Gal Rom, catat saja delta vertikal dan horizontal, dan dengan sedikit matematika Anda dapat menentukan jenis gesekan touchEvent itu. (Sekali lagi, izinkan saya menekankan bahwa ini SANGAT didasarkan pada jawaban sebelumnya, tetapi kesederhanaan mungkin menarik bagi pemula). Idenya adalah untuk memperluas OnTouchListener, mendeteksi jenis gesekan (sentuhan) yang baru saja terjadi dan memanggil metode tertentu untuk setiap jenis.public class SwipeListener implements View.OnTouchListener { private int min_distance = 100; private float downX, downY, upX, upY; View v; @Override public boolean onTouch(View v, MotionEvent event) { this.v = v; switch(event.getAction()) { // Check vertical and horizontal touches case MotionEvent.ACTION_DOWN: { downX = event.getX(); downY = event.getY(); return true; } case MotionEvent.ACTION_UP: { upX = event.getX(); upY = event.getY(); float deltaX = downX - upX; float deltaY = downY - upY; //HORIZONTAL SCROLL if (Math.abs(deltaX) > Math.abs(deltaY)) { if (Math.abs(deltaX) > min_distance) { // left or right if (deltaX < 0) { this.onLeftToRightSwipe(); return true; } if (deltaX > 0) { this.onRightToLeftSwipe(); return true; } } else { //not long enough swipe... return false; } } //VERTICAL SCROLL else { if (Math.abs(deltaY) > min_distance) { // top or down if (deltaY < 0) { this.onTopToBottomSwipe(); return true; } if (deltaY > 0) { this.onBottomToTopSwipe(); return true; } } else { //not long enough swipe... return false; } } return false; } } return false; } public void onLeftToRightSwipe(){ Toast.makeText(v.getContext(),"left to right", Toast.LENGTH_SHORT).show(); } public void onRightToLeftSwipe() { Toast.makeText(v.getContext(),"right to left", Toast.LENGTH_SHORT).show(); } public void onTopToBottomSwipe() { Toast.makeText(v.getContext(),"top to bottom", Toast.LENGTH_SHORT).show(); } public void onBottomToTopSwipe() { Toast.makeText(v.getContext(),"bottom to top", Toast.LENGTH_SHORT).show(); } }
sumber
Saya menulis kelas sederhana yang memudahkan untuk mendeteksi peristiwa swipe - ATAS, KANAN, BAWAH, KIRI.
1: Mendeteksi peristiwa gesekan tunggal
// Detect and consume specific events // {Available methods} - detectTop, detectRight, detectBottom, detectLeft SwipeEvents.detectTop(swipeElement, new SwipeEvents.SwipeSingleCallback() { @Override public void onSwipe() { showToast("Swiped - detectTop"); } });
2: Mendeteksi salah satu peristiwa gesekan dengan satu panggilan balik.
SwipeEvents.detect( swipeElement, new SwipeEvents.SwipeCallback() { @Override public void onSwipeTop() { //Swiped top } @Override public void onSwipeRight() { //Swiped right } @Override public void onSwipeBottom() { //Swiped bottom } @Override public void onSwipeLeft() { //Swiped left } });
Berikut adalah postingan blog dengan penjelasan tentang cara menggunakan: http://bmutinda.com/android-detect-swipe-events/
Saya juga telah membuat Inti untuk cuplikan kode yang tersedia di sini: https://gist.github.com/bmutinda/9578f70f1df9bd0687b8
Terima kasih.
sumber
Detektor Gesek Kiri ke Kanan dan Kanan ke Kiri
Pertama, nyatakan dua variabel tipe data float.
private float x1, x2;
Kedua, pasang tampilan xml Anda di java. Seperti yang saya miliki
ImageView
ImageView img = (ImageView) findViewById(R.id.imageView);
Ketiga,
setOnTouchListener
pada AndaImageView
.img.setOnTouchListener( new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { // TODO Auto-generated method stub switch (event.getAction()) { case MotionEvent.ACTION_DOWN: x1 = event.getX(); break; case MotionEvent.ACTION_UP: x2 = event.getX(); float deltaX = x2 - x1; if (deltaX < 0) { Toast.makeText(MainActivity.this, "Right to Left swipe", Toast.LENGTH_SHORT).show(); }else if(deltaX >0){ Toast.makeText(MainActivity.this, "Left to Right swipe", Toast.LENGTH_SHORT).show(); } break; } return false; } });
sumber
Saya ingin menambahkan pada jawaban yang diterima yang berfungsi sebagian, tetapi tidak memiliki variabel waktu, yang membuatnya sempurna.
Detektor gesekan kiri ke kanan paling sederhana dengan variabel waktu:
Di kelas aktivitas Anda, tambahkan atribut berikut:
private float x1,x2; private long startClickTime; static final int MIN_DISTANCE = 150; static final int MAX_SWIPE_TIME = 200;
dan timpa metode onTouchEvent ():
@Override public boolean onTouchEvent(MotionEvent event) { switch(event.getAction()) { case MotionEvent.ACTION_DOWN: startClickTime = Calendar.getInstance().getTimeInMillis(); x1 = event.getX(); break; case MotionEvent.ACTION_UP: long clickDuration = Calendar.getInstance().getTimeInMillis() - startClickTime; x2 = event.getX(); float deltaX = x2 - x1; if (Math.abs(deltaX) > MIN_DISTANCE && clickDuration < MAX_SWIPE_TIME) { Toast.makeText(this, "left2right swipe", Toast.LENGTH_SHORT).show (); } else { // consider as something else - a screen tap for example } break; } return super.onTouchEvent(event); }
sumber
Saya pikir apa yang Anda inginkan disebut selingkuh. MotionEvents dapat digunakan untuk menentukan arah lemparan.
public class MainActivity extends Activity implements GestureDetector.OnGestureListener { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.stellar_layout); mDetector = new GestureDetectorCompat(this, this); } @Override public boolean onFling(MotionEvent event1, MotionEvent event2, float velocityX, float velocityY) { Log.d(tag, "onFling:\n " + event1.toString()+ "\n " + event2.toString()); /* prints the following MotionEvent { action=ACTION_DOWN, id[0]=0, x[0]=297.0, y[0]=672.0, toolType[0]=TOOL_TYPE_FINGER, buttonState=0, metaState=0, flags=0x0, edgeFlags=0x0, pointerCount=1, historySize=0, eventTime=488341979, downTime=488341979, deviceId=6, source=0x1002 } MotionEvent { action=ACTION_UP, id[0]=0, x[0]=560.0, y[0]=583.0, toolType[0]=TOOL_TYPE_FINGER, buttonState=0, metaState=0, flags=0x0, edgeFlags=0x0, pointerCount=1, historySize=0, eventTime=488342047, downTime=488341979, deviceId=6, source=0x1002 } */ return true; } }
http://developer.android.com/training/gestures/detector.html
sumber
Deteksi gesekan dalam empat arah
private float x1,x2,y1,y2; static final int MIN_DISTANCE = 70;
dan
switch(pSceneTouchEvent.getAction()) { case MotionEvent.ACTION_DOWN: x1 = pSceneTouchEvent.getX(); y1 = pSceneTouchEvent.getY(); break; case MotionEvent.ACTION_UP: x2 = pSceneTouchEvent.getX(); y2 = pSceneTouchEvent.getY(); float deltaX = x2 - x1; float deltaY = y2 - y1; if (deltaX > MIN_DISTANCE) { swipeLeftToRight(); } else if( Math.abs(deltaX) > MIN_DISTANCE) { swipeRightToLeft(); } else if(deltaY > MIN_DISTANCE){ swipeTopToBottom(); } else if( Math.abs(deltaY) > MIN_DISTANCE){ swipeBottopmToTop(); } break; }
sumber
Setelah seharian mengerjakan fitur ini akhirnya bisa mendapatkan jawaban yang tepat.
import android.util.Log; import android.view.MotionEvent; import android.view.View; /** * Created by hoshyar on 1/19/17. */ public class SwipeDetector implements View.OnTouchListener { public static enum Action { LR, // Left to Right RL, // Right to Left TB, // Top to bottom BT, // Bottom to Top None // when no action was detected } private static final String logTag = "Swipe"; private static final int MIN_DISTANCE = 100; private float downX, downY, upX, upY; private Action mSwipeDetected = Action.None; public boolean swipeDetected() { return mSwipeDetected != Action.None; } public Action getAction() { return mSwipeDetected; } @Override public boolean onTouch(View v, MotionEvent event) { switch (event.getAction()) { case MotionEvent.ACTION_DOWN: downX = event.getX(); downY = event.getY(); mSwipeDetected = Action.None; return false; case MotionEvent.ACTION_MOVE: upX = event.getX(); upY = event.getY(); float deltaX = downX - upX; float deltaY = downY - upY; Log.i(logTag,String.valueOf(deltaX)); Log.i(logTag,String.valueOf(deltaX)); if (deltaY>0 && deltaY<10 && deltaX<0 || deltaY==0 && deltaX>-15 && deltaX<0){ Log.i(logTag,"to right"); }if (deltaY>=0 && deltaY<10 && deltaX>0 || deltaY<0 && deltaX>15 && deltaX<40){ Log.i(logTag,"to left"); } if (Math.abs(deltaX) > MIN_DISTANCE) { // left or right if (deltaX < 0) { mSwipeDetected = Action.LR; return false; } if (deltaX > 0) { mSwipeDetected = Action.RL; return false; } } else if (Math.abs(deltaY) > MIN_DISTANCE) { if (deltaY < 0) { Log.i(logTag,"to bottom"); mSwipeDetected = Action.TB; return false; } if (deltaY > 0) { Log.i(logTag,"to up"); mSwipeDetected = Action.BT; return false; } } return true; } return false; } }
SwipeDetector swipeDetector = new SwipeDetector(); listView.setOnTouchListener(swipeDetector);
Semoga berhasil .
sumber
Jika Anda ingin menangkap acara dari awal gesekan, Anda dapat menggunakan MotionEvent.ACTION_MOVE dan menyimpan nilai pertama untuk membandingkan
private float upX1; private float upX2; private float upY1; private float upY2; private boolean isTouchCaptured = false; static final int min_distance = 100; viewObject.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { switch (event.getAction()) { case MotionEvent.ACTION_MOVE: { downX = event.getX(); downY = event.getY(); if (!isTouchCaptured) { upX1 = event.getX(); upY1 = event.getY(); isTouchCaptured = true; } else { upX2 = event.getX(); upY2 = event.getY(); float deltaX = upX1 - upX2; float deltaY = upY1 - upY2; //HORIZONTAL SCROLL if (Math.abs(deltaX) > Math.abs(deltaY)) { if (Math.abs(deltaX) > min_distance) { // left or right if (deltaX < 0) { return true; } if (deltaX > 0) { return true; } } else { //not long enough swipe... return false; } } //VERTICAL SCROLL else { if (Math.abs(deltaY) > min_distance) { // top or down if (deltaY < 0) { return false; } if (deltaY > 0) { return false; } } else { //not long enough swipe... return false; } } } return false; } case MotionEvent.ACTION_UP: { isTouchCaptured = false; } } return false; } });
sumber
Toast.makeText(MainAcivity.this, "top to down" + increaseValue, Toast.LENGTH_SHORT).show();
dia bagaimana membuat satu gesekan untuk menambahkan nilai min = 0 dan max = 10.ini akan membantu Anda mungkin ...
private final GestureDetector.SimpleOnGestureListener onGestureListener = new GestureDetector.SimpleOnGestureListener() { @Override public boolean onDoubleTap(MotionEvent e) { Log.i("gestureDebug333", "doubleTapped:" + e); return super.onDoubleTap(e); } @Override public boolean onDoubleTapEvent(MotionEvent e) { Log.i("gestureDebug333", "doubleTappedEvent:" + e); return super.onDoubleTapEvent(e); } @Override public boolean onDown(MotionEvent e) { Log.i("gestureDebug333", "onDown:" + e); return super.onDown(e); } @Override public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { Log.i("gestureDebug333", "flinged:" + e1 + "---" + e2); Log.i("gestureDebug333", "fling velocity:" + velocityX + "---" + velocityY); if (e1.getAction() == MotionEvent.ACTION_DOWN && e1.getX() > (e2.getX() + 300)){ // Toast.makeText(context, "flinged right to left", Toast.LENGTH_SHORT).show(); goForward(); } if (e1.getAction() == MotionEvent.ACTION_DOWN && e2.getX() > (e1.getX() + 300)){ //Toast.makeText(context, "flinged left to right", Toast.LENGTH_SHORT).show(); goBack(); } return super.onFling(e1, e2, velocityX, velocityY); } @Override public void onLongPress(MotionEvent e) { super.onLongPress(e); } @Override public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) { return super.onScroll(e1, e2, distanceX, distanceY); } @Override public void onShowPress(MotionEvent e) { super.onShowPress(e); } @Override public boolean onSingleTapConfirmed(MotionEvent e) { return super.onSingleTapConfirmed(e); } @Override public boolean onSingleTapUp(MotionEvent e) { return super.onSingleTapUp(e); } };
sumber
Versi singkat dan mudah:
1. Pertama buat kelas abstrak ini
public abstract class HorizontalSwipeListener implements View.OnTouchListener { private float firstX; private int minDistance; HorizontalSwipeListener(int minDistance) { this.minDistance = minDistance; } abstract void onSwipeRight(); abstract void onSwipeLeft(); @Override public boolean onTouch(View view, MotionEvent event) { switch (event.getAction()) { case MotionEvent.ACTION_DOWN: firstX = event.getX(); return true; case MotionEvent.ACTION_UP: float secondX = event.getX(); if (Math.abs(secondX - firstX) > minDistance) { if (secondX > firstX) { onSwipeLeft(); } else { onSwipeRight(); } } return true; } return view.performClick(); } }
2. Kemudian buat kelas konkret yang menerapkan apa yang Anda butuhkan:
public class SwipeListener extends HorizontalSwipeListener { public SwipeListener() { super(200); } @Override void onSwipeRight() { System.out.println("right"); } @Override void onSwipeLeft() { System.out.println("left"); } }
sumber
berikut adalah detektor geser ke kiri generik untuk tampilan apa pun di kotlin menggunakan penyatuan data
@BindingAdapter("onSwipeLeft") fun View.setOnSwipeLeft(runnable: Runnable) { setOnTouchListener(object : View.OnTouchListener { var x0 = 0F; var y0 = 0F; var t0 = 0L val defaultClickDuration = 200 override fun onTouch(v: View?, motionEvent: MotionEvent?): Boolean { motionEvent?.let { event -> when(event.action) { MotionEvent.ACTION_DOWN -> { x0 = event.x; y0 = event.y; t0 = System.currentTimeMillis() } MotionEvent.ACTION_UP -> { val x1 = event.x; val y1 = event.y; val t1 = System.currentTimeMillis() if (x0 == x1 && y0 == y1 && (t1 - t0) < defaultClickDuration) { performClick() return false } if (x0 > x1) { runnable.run() } } else -> {} } } return true } }) }
dan kemudian menggunakannya dalam tata letak Anda:
app:onSwipeLeft="@{() -> viewModel.swipeLeftHandler()}"
sumber
public class TransferMarket extends Activity { float x1,x2; float y1, y2; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_transfer_market); } // onTouchEvent () method gets called when User performs any touch event on screen // Method to handle touch event like left to right swap and right to left swap public boolean onTouchEvent(MotionEvent touchevent) { switch (touchevent.getAction()) { // when user first touches the screen we get x and y coordinate case MotionEvent.ACTION_DOWN: { x1 = touchevent.getX(); y1 = touchevent.getY(); break; } case MotionEvent.ACTION_UP: { x2 = touchevent.getX(); y2 = touchevent.getY(); //if left to right sweep event on screen if (x1 < x2) { Toast.makeText(this, "Left to Right Swap Performed", Toast.LENGTH_LONG).show(); } // if right to left sweep event on screen if (x1 > x2) { Toast.makeText(this, "Right to Left Swap Performed", Toast.LENGTH_LONG).show(); } // if UP to Down sweep event on screen if (y1 < y2) { Toast.makeText(this, "UP to Down Swap Performed", Toast.LENGTH_LONG).show(); } //if Down to UP sweep event on screen if (y1 > y2) { Toast.makeText(this, "Down to UP Swap Performed", Toast.LENGTH_LONG).show(); } break; } } return false; }
sumber
jawaban terbaik adalah @Gal Rom's. ada lebih banyak informasi tentang itu: sentuh acara kembali ke tampilan anak terlebih dahulu. dan jika Anda menentukan onClick atau pendengar onTouch untuk mereka, tampilan parnt (misalnya fragmen) tidak akan menerima pendengar sentuh apa pun. Jadi, jika Anda ingin menentukan pemroses gesek untuk fragmen dalam situasi ini, Anda harus mengimplementasikannya di kelas baru:
package com.neganet.QRelations.fragments; import android.content.Context; import android.util.AttributeSet; import android.view.MotionEvent; import android.widget.FrameLayout; public class SwipeListenerFragment extends FrameLayout { private float x1,x2; static final int MIN_DISTANCE=150; private onSwipeEventDetected mSwipeDetectedListener; public SwipeListenerFragment(Context context) { super(context); } public SwipeListenerFragment(Context context, AttributeSet attrs) { super(context, attrs); } public SwipeListenerFragment(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } @Override public boolean onInterceptTouchEvent(MotionEvent ev) { boolean result=false; switch(ev.getAction()) { case MotionEvent.ACTION_DOWN: x1 = ev.getX(); break; case MotionEvent.ACTION_UP: x2 = ev.getX(); float deltaX = x2 - x1; if (Math.abs(deltaX) > MIN_DISTANCE) { if(deltaX<0) { result=true; if(mSwipeDetectedListener!=null) mSwipeDetectedListener.swipeLeftDetected(); }else if(deltaX>0){ result=true; if(mSwipeDetectedListener!=null) mSwipeDetectedListener.swipeRightDetected(); } } break; } return result; } public interface onSwipeEventDetected { public void swipeLeftDetected(); public void swipeRightDetected(); } public void registerToSwipeEvents(onSwipeEventDetected listener) { this.mSwipeDetectedListener=listener; } }
Saya mengubah kelas @Gal Rom. Sehingga dapat mendeteksi gesekan kanan dan kiri dan secara khusus mengembalikan onInterceptTouchEvent true setelah mendeteksi. ini penting karena jika kita tidak melakukannya beberapa kali tampilan anak mungkin menerima peristiwa dan kedua Swipe untuk fragmen dan onClick untuk tampilan anak (misalnya) berjalan dan menyebabkan beberapa masalah. setelah membuat kelas ini, Anda harus mengubah file xml fragmen Anda:
<com.neganet.QRelations.fragments.SwipeListenerFragment xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:id="@+id/main_list_layout" android:clickable="true" android:focusable="true" android:focusableInTouchMode="true" android:layout_height="match_parent" tools:context="com.neganet.QRelations.fragments.mainList" android:background="@color/main_frag_back"> <!-- TODO: Update blank fragment layout --> <android.support.v7.widget.RecyclerView android:id="@+id/farazList" android:scrollbars="horizontal" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_gravity="left|center_vertical" /> </com.neganet.QRelations.fragments.SwipeListenerFragment>
Anda melihat bahwa tag awal adalah kelas yang kami buat. sekarang di kelas fragmen:
View view=inflater.inflate(R.layout.fragment_main_list, container, false); SwipeListenerFragment tdView=(SwipeListenerFragment) view; tdView.registerToSwipeEvents(this); and then Implement SwipeListenerFragment.onSwipeEventDetected in it: @Override public void swipeLeftDetected() { Toast.makeText(getActivity(), "left", Toast.LENGTH_SHORT).show(); } @Override public void swipeRightDetected() { Toast.makeText(getActivity(), "right", Toast.LENGTH_SHORT).show(); }
Agak rumit tetapi berfungsi dengan sempurna :)
sumber
Anda harus memperluas kelas dari
View.OnTouchListener
dan menanganionTouch
metode dengan menimpanya.interface SwipeListener { fun onSwipeLeft() fun onSwipeRight() } class SwipeGestureListener internal constructor( private val listener: SwipeListener, private val minDistance: Int = DEFAULT_SWIPE_MIN_DISTANCE ) : View.OnTouchListener { companion object { const val DEFAULT_SWIPE_MIN_DISTANCE = 200 } private var anchorX = 0F override fun onTouch(view: View, event: MotionEvent): Boolean { when (event.action) { MotionEvent.ACTION_DOWN -> { anchorX = event.x return true } MotionEvent.ACTION_UP -> { if (abs(event.x - anchorX) > minDistance) { if (event.x > anchorX) { listener.onSwipeRight() } else { listener.onSwipeLeft() } } return true } } return view.performClick() } }
Anda dapat dengan mudah menerapkannya seperti ini di
Activity
atauFragment
.class MainActivity : AppCompatActivity(), SwipeListener { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) viewGroup.setOnTouchListener(SwipeGestureListener(this)) } override fun onSwipeLeft() { Toast.makeText(this, "Swipe Left", Toast.LENGTH_SHORT).show() } override fun onSwipeRight() { Toast.makeText(this, "Swipe Right", Toast.LENGTH_SHORT).show() } }
sumber