簡體   English   中英

Android:onTouchListener無法正常工作

[英]Android: onTouchListener not working properly

我目前正在開發一個帶有4個子FrameLayoutsRelativeLayout的應用程序,每個FrameLayout內部都有一組ImageViews,而View內部有它自己的行為。 在實現本教程中發現的onTouchListener同時,我試圖實現對FrameLayouts的拖放。 但不幸的是,拖放操作無法正常進行,並且沒有任何反應。

關於如何正確執行拖放的任何想法? 我想念什么?


這是FrameLayouts的單個子FrameLayouts的xml代碼:

 <?xml version="1.0" encoding="utf-8"?> <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="80dp" android:layout_height="108dp" > <ImageView android:id="@+id/secondImage" android:layout_width="fill_parent" android:layout_height="fill_parent" android:src="@drawable/back" /> <ImageView android:id="@+id/firstImage" android:layout_width="fill_parent" android:layout_height="fill_parent" android:src="@drawable/c2" /> </FrameLayout> 


這是main.xml的xml代碼

 <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="fill_parent" android:background="@drawable/pinecropped" android:orientation="vertical" > <FrameLayout android:id="@+id/cardNumber1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="50dp" android:layout_marginTop="60dp" > <include layout="@layout/card" /> </FrameLayout> <FrameLayout android:id="@+id/cardNumber2" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_below="@+id/cardNumber1" android:layout_marginLeft="50dp" android:layout_marginTop="100dp" > <include layout="@layout/card" /> </FrameLayout> <FrameLayout android:id="@+id/cardNumber3" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" android:layout_marginRight="50dp" android:layout_marginTop="60dp" > <include layout="@layout/card" /> </FrameLayout> <FrameLayout android:id="@+id/cardNumber4" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" android:layout_below="@+id/cardNumber3" android:layout_marginRight="50dp" android:layout_marginTop="100dp" > <include layout="@layout/card" /> </FrameLayout> </RelativeLayout> 


這是單個孩子的Java代碼:

public class FaceUpActivity extends Activity {
    FrameLayout firstCard, secondCard, thirdCard, forthCard;
    Card cardNumber1, cardNumber2, cardNumber3, cardNumber4;

    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        initUI();
    }

    private void initUI() {
        firstCard = (FrameLayout) findViewById(R.id.cardNumber1);
        secondCard = (FrameLayout) findViewById(R.id.cardNumber2);
        thirdCard = (FrameLayout) findViewById(R.id.cardNumber3);
        forthCard = (FrameLayout) findViewById(R.id.cardNumber4);

        cardNumber1 = new Card(this, firstCard);
        cardNumber2 = new Card(this, secondCard);
        cardNumber3 = new Card(this, thirdCard);
        cardNumber4 = new Card(this, forthCard);

        cardNumber1.setupCards(R.drawable.c2, true);
        cardNumber2.setupCards(R.drawable.d0, true);
        cardNumber3.setupCards(R.drawable.h5, true);
        cardNumber4.setupCards(R.drawable.sj, true);

        firstCard.setOnTouchListener(dragMe);
        secondCard.setOnTouchListener(dragMe);
        thirdCard.setOnTouchListener(dragMe);
        forthCard.setOnTouchListener(dragMe);

    }

    OnTouchListener dragMe = new OnTouchListener() {

        @Override
        public boolean onTouch(View v, MotionEvent event) {
            FrameLayout.LayoutParams params = (LayoutParams) v
                    .getLayoutParams();
            int maxWidth = getWindowManager().getDefaultDisplay().getWidth();
            int maxHeight = getWindowManager().getDefaultDisplay().getHeight();
            int topMargin, leftMargin;

            int cond = v.getId();
            if (cond == R.id.cardNumber1 || cond == R.id.cardNumber2
                    || cond == R.id.cardNumber3 || cond == R.id.cardNumber4) {
                switch (event.getAction()) {
                case MotionEvent.ACTION_UP:

                    topMargin = (int) event.getRawY() - (v.getHeight());
                    leftMargin = (int) event.getRawX() - (v.getWidth()) / 2;

                    if (topMargin < 0) {
                        params.topMargin = 0;
                    } else if (topMargin > maxHeight) {
                        params.topMargin = maxHeight - v.getHeight();
                    } else {
                        params.topMargin = topMargin;
                    }

                    if (leftMargin < 0) {
                        params.leftMargin = 0;
                    } else if (leftMargin > maxWidth) {
                        params.leftMargin = maxWidth - (v.getWidth() / 2);
                    } else {
                        params.leftMargin = leftMargin;
                    }

                    v.setLayoutParams(params);

                    break;

                case MotionEvent.ACTION_MOVE:

                    topMargin = (int) event.getRawY() - (v.getHeight());
                    leftMargin = (int) event.getRawX() - (v.getWidth()) / 2;

                    if (topMargin < 0) {
                        params.topMargin = 0;
                    } else if (topMargin > maxHeight) {
                        params.topMargin = maxHeight - v.getHeight();
                    } else {
                        params.topMargin = topMargin;
                    }

                    if (leftMargin < 0) {
                        params.leftMargin = 0;
                    } else if (leftMargin > maxWidth) {
                        params.leftMargin = maxWidth - (v.getWidth() / 2);
                    } else {
                        params.leftMargin = leftMargin;
                    }

                    v.setLayoutParams(params);

                    break;
                }
            }
            return true;
        }
    };
}


這是我的主要活動Java代碼:

 public class FaceUpActivity extends Activity { FrameLayout firstCard, secondCard, thirdCard, forthCard; Card cardNumber1, cardNumber2, cardNumber3, cardNumber4; /** Called when the activity is first created. */ @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); initUI(); } private void initUI() { firstCard = (FrameLayout) findViewById(R.id.cardNumber1); secondCard = (FrameLayout) findViewById(R.id.cardNumber2); thirdCard = (FrameLayout) findViewById(R.id.cardNumber3); forthCard = (FrameLayout) findViewById(R.id.cardNumber4); cardNumber1 = new Card(this, firstCard); cardNumber2 = new Card(this, secondCard); cardNumber3 = new Card(this, thirdCard); cardNumber4 = new Card(this, forthCard); cardNumber1.setupCards(R.drawable.c2, true); cardNumber2.setupCards(R.drawable.d0, true); cardNumber3.setupCards(R.drawable.h5, true); cardNumber4.setupCards(R.drawable.sj, true); firstCard.setOnTouchListener(dragMe); secondCard.setOnTouchListener(dragMe); thirdCard.setOnTouchListener(dragMe); forthCard.setOnTouchListener(dragMe); } OnTouchListener dragMe = new OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { FrameLayout.LayoutParams params = (LayoutParams) v .getLayoutParams(); int maxWidth = getWindowManager().getDefaultDisplay().getWidth(); int maxHeight = getWindowManager().getDefaultDisplay().getHeight(); int topMargin, leftMargin; int cond = v.getId(); if (cond == R.id.cardNumber1 || cond == R.id.cardNumber2 || cond == R.id.cardNumber3 || cond == R.id.cardNumber4) { switch (event.getAction()) { case MotionEvent.ACTION_UP: topMargin = (int) event.getRawY() - (v.getHeight()); leftMargin = (int) event.getRawX() - (v.getWidth()) / 2; if (topMargin < 0) { params.topMargin = 0; } else if (topMargin > maxHeight) { params.topMargin = maxHeight - v.getHeight(); } else { params.topMargin = topMargin; } if (leftMargin < 0) { params.leftMargin = 0; } else if (leftMargin > maxWidth) { params.leftMargin = maxWidth - (v.getWidth() / 2); } else { params.leftMargin = leftMargin; } v.setLayoutParams(params); break; case MotionEvent.ACTION_MOVE: topMargin = (int) event.getRawY() - (v.getHeight()); leftMargin = (int) event.getRawX() - (v.getWidth()) / 2; if (topMargin < 0) { params.topMargin = 0; } else if (topMargin > maxHeight) { params.topMargin = maxHeight - v.getHeight(); } else { params.topMargin = topMargin; } if (leftMargin < 0) { params.leftMargin = 0; } else if (leftMargin > maxWidth) { params.leftMargin = maxWidth - (v.getWidth() / 2); } else { params.leftMargin = leftMargin; } v.setLayoutParams(params); break; } } return true; } }; } 

我認為有兩個潛在問題:

  1. 您確定在onTouch()獲得正確的ID嗎? (由於觸摸監聽器僅用於您的名片視圖,因此, if檢查ID, if可以刪除)
  2. 您正在使用 FrameLayout因此請使用x和y位置而不是margins 編輯:不好,您正在使用RelativeLayout ,因此margins是正確的。 不過,我會改用FrameLayout
  3. API指出,如果您消耗了事件,則需要在onTouch()返回true ,否則返回false (當您不移動卡時,您將返回true當您不進行操作時,您將不返回)

為什么您的D&D無法正常工作:

D&D無法正常工作,因為您的Card(使用內部FrameLayout)正在實現“吞噬” d&d事件的onClick事件。

解決方法有兩種:

您可以有2個不同的區域,一個區域用於單擊事件(卡的最大部分),一個區域用於d&d事件(卡的左下邊緣)。 您可以在實現此解決方案的Android音樂播放器中看到一個實時示例。

否則,您可以同時處理兩個事件:

  • 在同一x / y位置同時(= 100毫秒內)單擊==向下+向上
  • dd ==在不同時間向下+向上(> 50 / 100ms)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM