2011-03-25 9 views
8

Hola Estoy tratando de hacer un arrastrar y soltar en un ListView. Funciona muy bien. Pero perdí la capacidad de hacer clic y desplazarme. ¿Cómo puedo conservar esos dos? Pensaba que la operación de arrastrar y soltar debería ocurrir con una pulsación larga del elemento en lugar de presionarlo normalmente. Aquí está mi onTouch que se encuentra en el MyListView que se extiende ListViewdesplazamiento androide, mientras que arrastrar y soltar

@Override 
    public boolean onTouchEvent(MotionEvent ev) { 
     final int action = ev.getAction(); 
     final int x = (int) ev.getX(); 
     final int y = (int) ev.getY(); 

     if (action == MotionEvent.ACTION_DOWN && x < this.getWidth()/4) { 
      this._dragMode = true; 
     } 

     if (!this._isDragNDrop) 
      return super.onTouchEvent(ev); 

     switch (action) { 
      case MotionEvent.ACTION_DOWN: 
       this._startPosition = pointToPosition(x,y); 
       if (this._startPosition != INVALID_POSITION) { 
        int mItemPosition = this._startPosition - getFirstVisiblePosition(); 
        this._dragPointOffset = y - getChildAt(mItemPosition).getTop(); 
        this._dragPointOffset -= ((int)ev.getRawY()) - y; 
        startDrag(mItemPosition,y); 
        drag(x,y); 
       } 
       break; 
      case MotionEvent.ACTION_MOVE: 
       drag(x,y); 
       break; 
      case MotionEvent.ACTION_CANCEL: 
      case MotionEvent.ACTION_UP: 
      default: 
       this._dragMode = false; 
       //_isDragNDrop = false; 
       this._endPosition = pointToPosition(x,y); 
       stopDrag(this._startPosition - getFirstVisiblePosition()); 
       if (this._dropListener != null && this._startPosition != INVALID_POSITION && this._endPosition != INVALID_POSITION) 
        this._dropListener.onDrop(this._startPosition, this._endPosition); 
       break; 
     } 
     return true; 
    } 

Respuesta

5

simplemente he implementado arrastrarlo vista de lista en mi solicitud, los empieza a arrastrar por pulsación larga en un elemento.

El código fuente está en GitHub: DraggableListView, tengo un blog post para describirlo. Espero que te ayude

+0

wow, ¡muchas gracias! Decidimos posponer esta función debido a que no pudimos hacerlo funcionar. Voy a ver esto y ver si esto resuelve mi problema. Vi tu blog, es cierto que tomaría más de una semana, cuando llegué a los dos días y tuve que dejarlo :) – dropsOfJupiter

+0

¡excelente componente! Funciona bien para mí ... THX – kyp

+0

El enlace del blog post anterior no funciona, pero se puede encontrar el resto de lo que se necesita aquí: http://codegarage.no-ip.co.uk/snippets/94 – mpemburn

2

Consulte este question para obtener ayuda adicional. También tengo un componente llamado DragSortListView que he pasado mucho tiempo refinando. Lo puedes encontrar aquí:

pude ayudarle a integrar largo de prensa inició arrastrando en un tenedor de mi repo anteriormente.

+0

Cool library :) –

3

estoy poniendo en práctica algo similar. Espero que esto ayude a otra persona ya que todavía estoy resolviendo los problemas.

... 
thumb.setOnDragListener(new Drag()); 
... 

public class Drag implements OnDragListener{ 
public static int PositionOfDraggedItem = -1; 
     public int PositionOfItemDraggedOver = -1; 

public Drag() {} 

@Override 
public boolean onDrag(View v, DragEvent event) 
{ 
    final int action = event.getAction(); 
    boolean state = true; 

    View root = v.getRootView(); 
    ListView List = (ListView) root.findViewById(android.R.id.list); 
    Object holder = v.getTag() instanceof OrderHolder? (OrderHolder)v.getTag() : v.getTag(); 

    String BookId = holder instanceof OrderHolder? String.valueOf(((OrderHolder)holder).id) : (String)holder; 

    switch(action) 
    { 
     case DragEvent.ACTION_DRAG_STARTED: 

      break; 
     case DragEvent.ACTION_DRAG_ENTERED: 
      if(PositionOfDraggedItem != -1) 
      { 
       if(this.PositionOfItemDraggedOver != PositionOfDraggedItem) 
       { 
        if(v.getBackground() != null) 
         v.setBackgroundDrawable(v.getContext().getResources().getDrawable(drawable.row_ovr)); 
       } 
      } 
      break; 
     case DragEvent.ACTION_DRAG_LOCATION: 
      /** 
      * Set the item being 
      * here, as it will not 
      * provide location data 
      * anywhere else 
      */ 
      if(PositionOfDraggedItem == -1) 
       PositionOfDraggedItem = List.getPositionForView(v); 

      /** 
      * Set the view thats 
      * being dragged over 
      */ 
      this.PositionOfItemDraggedOver = List.getPositionForView(v); 

      int PositionOfLastVisibleView = List.getLastVisiblePosition(); 
      int PositionOfFirstVisibleView = List.getFirstVisiblePosition(); 

      if(this.PositionOfItemDraggedOver != -1 && (this.PositionOfItemDraggedOver != PositionOfDraggedItem)){ 
       if(this.PositionOfItemDraggedOver == PositionOfLastVisibleView-1 || this.PositionOfItemDraggedOver == PositionOfLastVisibleView || this.PositionOfItemDraggedOver == PositionOfLastVisibleView+1){ 
        List.smoothScrollToPosition(PositionOfLastVisibleView+1); 
       }else if(this.PositionOfItemDraggedOver == PositionOfFirstVisibleView-1 || this.PositionOfItemDraggedOver == PositionOfFirstVisibleView+1 || this.PositionOfItemDraggedOver == PositionOfFirstVisibleView){ 
        List.smoothScrollToPosition(PositionOfFirstVisibleView-1); 
       } 
      } 
      break; 
     case DragEvent.ACTION_DRAG_EXITED: 
      if(v.getBackground() != null) 
       v.setBackgroundDrawable(v.getContext().getResources().getDrawable(drawable.row)); 
      break; 
     case DragEvent.ACTION_DROP: 
      if(event != null) 
      { 
       ClipData data = event.getClipData(); 
       if(data != null && data.getItemCount() > 0) 
       { 
        if(!data.getItemAt(0).getText().toString().equalsIgnoreCase(BookId)) 
        { 
         if(v.getBackground() != null) 
          v.setBackgroundDrawable(v.getContext().getResources().getDrawable(drawable.row)); 
         /** 
         * Ordering info for 
         * book being dragged 
         */ 
         String oShelfOrder = BookManager.item(v.getContext().getContentResolver(), dbhelper.BOOKS_SHELFORDER, 
           booksprovider.GetUri(dbhelper.BOOKS), Long.parseLong(data.getItemAt(0).getText().toString())); 
         String oBookOrder = BookManager.item(v.getContext().getContentResolver(), dbhelper.BOOKS_BOOKSORDER, 
           booksprovider.GetUri(dbhelper.BOOKS), Long.parseLong(data.getItemAt(0).getText().toString())); 

         /** 
         * Ordering info 
         * for book being dragged 
         * to 
         */ 
         String dShelfOrder = BookManager.item(v.getContext().getContentResolver(), dbhelper.BOOKS_SHELFORDER, 
           booksprovider.GetUri(dbhelper.BOOKS), Long.parseLong(BookId)); 
         String dBookOrder = BookManager.item(v.getContext().getContentResolver(), dbhelper.BOOKS_BOOKSORDER, 
           booksprovider.GetUri(dbhelper.BOOKS), Long.parseLong(BookId)); 

         /** 
         * Update book being dragged 
         */ 
         ContentValues args = new ContentValues(); 
         args.put(dbhelper.BOOKS_SHELFORDER, dShelfOrder); 
         args.put(dbhelper.BOOKS_BOOKSORDER, dBookOrder); 
         BookManager.updateBook(v.getContext().getContentResolver(), data.getItemAt(0).getText().toString(), args); 

         /** 
         * Update book being dragged to 
         */ 
         ContentValues values = new ContentValues(); 
         values.put(dbhelper.BOOKS_SHELFORDER, oShelfOrder); 
         values.put(dbhelper.BOOKS_BOOKSORDER, oBookOrder); 
         BookManager.updateBook(v.getContext().getContentResolver(), BookId, values); 

         if(v.getContext() instanceof OrderBooks){ 
          ((OrderBooks)v.getContext()).adapter.refresh(); 
          ((OrderBooks)v.getContext()).adapter.notifyDataSetChanged(); 

          PositionOfDraggedItem = -1; 
         } 
        } 
       } 
      } 
      break; 
     case DragEvent.ACTION_DRAG_ENDED: 
      if(event != null && event.getResult()) 
      { 
       v.invalidate(); 
      } 
      break; 
    } 
    return state; 
} 

}

no han trabajado en ella en cuando, actualizado para reflejar los cambios más recientes.

+0

smoothScrollToPosition iniciará un scroller anim cada vez, y creo que lo mejor es publicar un smoothScrollToPosition (amount, linear) cada 1 segundo, pero este método no es público ni está protegido ... – molikto

+0

This la solución se desplaza perfectamente, sin embargo, los DragListeners de Vistas en la lista que no estaban visibles antes del desplazamiento no reaccionan al arrastrar. Cuando arrastro un objeto al área inferior de la vista de lista, se desplaza hacia abajo, pero DragListener en las vistas que se vuelven visibles al desplazarse no obtiene ningún evento. Funcionan como de costumbre cuando puedo alcanzarlos sin desplazarme. ¿Alguno de ustedes encontró una solución para esto? –

0

he implementado esta solución que funciona para mí. El siguiente método está en mi Actividad y se llama en mi dragEventListener cuando el dragEvent es ACTION_DRAG_ENTERED. Algunos atributos que declararon:

//first visible item (getFirstVisiblePosition() does not work for me) 
int firstVisible; 
//number of scrolls 
int nbrScroll; 
//my listview to scroll 
ListView mListView; 
//the adapter of my listview 
SimpleAdapter mAdapter; 

...

public void scrollDrag(int position) { 
      //this is the position of the item in my listview 
      //to scroll down 
      //test if the item entered is the last visible 
    if (position == mListView.getLastVisiblePosition() 
      && id < mListView.getCount()) { 
     mAdapter.notifyDataSetChanged(); 
     mRightDrawerList.post(new Runnable() { 
      @Override 
      public void run() { 
       //scroll down 
       mListView.smoothScrollToPosition(mListView 
         .getLastVisiblePosition() + 1); 
       firstVisible++; 
      } 
     }); 
      //to scroll up 
      //test if the item entered is the first visible 
    } else if (position == firstVisible && position !=0) { 
     mAdapter.notifyDataSetChanged(); 
     mListView.post(new Runnable() { 
      @Override 
      public void run() { 
       //scroll up 
       mListView.smoothScrollToPosition(firstVisible-1); 
       firstVisible --; 
      } 
     }); 
    } 
} 

esperan que ayude a alguien.

-1

He hecho pequeños cambios en el código de rickey y me sirve.

if (PositionOfItemDraggedOver == PositionOfLastVisibleView) 
    order_item_list_lv.smoothScrollToPosition(PositionOfLastVisibleView + 1); 

if (PositionOfItemDraggedOver == PositionOfFirstVisibleView) 
    order_item_list_lv.smoothScrollToPosition(PositionOfFirstVisibleView - 1);