0

I am trying to impement Androids drag and drop on my gridview. I set a dragListener for each view in the grid adapter. It works perfectly when the grid isn't long enough to be scrollable or if it is scrollable as long as the first view in the grid is visible. When scrolled it is moving the actions down a position for however many views are not visible at the top instead of being at the correct position.

GridView set DragListener inside of the adapter:

ImageView i = new ImageView;
i.setImageResource(ImageList.get(position));
i.setOnDragListener(new MyDragImageListener(position));
return i;

MyDragListener:

public class MyDragImageListener implements OnDragListener{

    int imagePosition;

    public MyDragImageListener(int position) {
        imagePosition = position;
    }

    @Override
    public boolean onDrag(View v, DragEvent event) {
        switch (event.getAction()) {
        case DragEvent.ACTION_DRAG_STARTED:
            Log.i("DRAG Started", "" + imagePosition);
          break;
        case DragEvent.ACTION_DRAG_ENTERED:
            Log.i("DRAG Entered", "" + imagePosition);
            ImageView imageEnter = (ImageView) Grid.getChildAt(imagePosition);
            imageEnter.setBackgroundColor(Color.argb(155, 100, 200, 255));
          break;
        case DragEvent.ACTION_DRAG_EXITED:        
            Log.i("DRAG Exited", "" + imagePosition);
            ImageView imageExit = (ImageView) Grid.getChildAt(imagePosition);
            imageExit.setBackgroundColor(Color.argb(0, 0, 0, 0));
          break;
        case DragEvent.ACTION_DROP:
            Log.i("DRAG Dropped", "" + imagePosition);

          break;
        case DragEvent.ACTION_DRAG_ENDED:
            Log.i("DRAG Ended", "" + imagePosition);
          default:
          break;
        }
        return true;
    }

}
cange1
  • 641
  • 5
  • 5
  • 1
    You wanna say that DragEvent is returning screenPosition and you are expecting absolute position or other way around? Why don't you just get that scroll position and use that as offset – Marko Lazić May 19 '13 at 21:11
  • thanks I tried this and it seems like it works. I just started using the drag and drop and thought it would be a much more complicated solution and never thought to try that. – cange1 May 20 '13 at 22:43

1 Answers1

0

How are you handling the touch events? There is thin balance between offering all the touch actions in one single place:

    @Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
    if (mDragController == null || !mDragging) {
        if (mDragController!=null) mDragController.onInterceptTouchEvent(ev);
        if (mSwipeEnabled) {
            gestureDetector.onTouchEvent(ev);
            return false; //to make sure we receive further messages
        }
        else
            return super.onInterceptTouchEvent(ev); //for scroll, etc
    }
    else
    // controller to handle event
    return mDragController.onInterceptTouchEvent(ev);
}

/**
 * 
 */
@Override
public boolean onTouchEvent(MotionEvent ev) {
    if (mDragController == null || !mDragging) {
        //if (!gestureDetector.onTouchEvent(ev))
            return super.onTouchEvent(ev);
    }
    // controller to handle event
    return mDragController.onTouchEvent(ev);
}

This works great, providing the results illustrated in this demo video: http://www.youtube.com/watch?v=m4yktX3SWSs (source code link in video description).

radhoo
  • 2,877
  • 26
  • 27