2010-03-22 2 views
2

как бы вы предотвратили перетаскивание для некоторых элементов вашего списка или DataGrid?Flex - предотвращение перетаскивания для определенных предметов

Предположим, у меня был список с двумя пунктами: «Том» и «Джерри». Только «Том» должен быть перетаскиваемым, а не «Джерри».

В идеале у меня была функция isDragEnabled (item: Object): Boolean ', которая запрашивается источником перетаскивания.

Мои трудности начинаются с того, что обработчик события «dragStart» имеет нулевое значение для DragSource, поэтому с самого начала я считаю, что это трудно выяснить, что перетащить начало примерно ..

Заранее спасибо!

PS Было несколько обсуждений по предотвращению или отмене падения, но я не видел многого о предотвращении начала перетаскивания, следовательно, этого вопроса.

ответ

1

Хорошо, он получил, благодаря Робусто, ваш Совет № 2 был вдохновением, однако я должен был использовать мышь вниз слушателя - отбор пожаров событий слишком поздно.

В приведенном ниже примере я использую код от some other question.

Этот пример позволяет перетаскивать только первый элемент в списке или DataGrid:

<?xml version="1.0" encoding="utf-8"?> 
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="horizontal" minWidth="955" minHeight="600"> 

    <mx:List id="list" dataProvider="{['Tom','Jerry', 'Amy', 'Betty', 'Chris', 'Dean', 'Email', 'Floyd', 'Grant', 'Helen', 'Iris', 'Jack']}" minWidth="200" 
     mouseDown="onMouseDown(event)" 
     /> 

    <mx:DataGrid id="dg" dataProvider="{[{title:'Tom'},{title:'Jerry'}]}" minWidth="200" 
     mouseDown="onMouseDown(event)" 
    > 
     <mx:columns> 
      <mx:DataGridColumn dataField="title" /> 
     </mx:columns> 
    </mx:DataGrid> 

    <mx:Script> 
     <![CDATA[ 
      import mx.controls.listClasses.ListBase; 
      import mx.events.DragEvent; 


      protected function onMouseDown(event:MouseEvent):void 
      { 
       var listBaseComp:ListBase = ListBase(event.currentTarget); 
       var clickIndex:int = this.findClickedItemIndex(event.stageX, event.stageY, listBaseComp); 
       listBaseComp.dragEnabled = clickIndex == 0; 
      } 

      /** 
      * Returns a dataProvider item that displays at the given coords for the given dataGrid. 
      * Code provided by Stackoverflow user https://stackoverflow.com/users/165297/amarghosh, 
      * thanks a lot! 
      */ 
      protected function findClickedItemIndex(globalX:Number, globalY:Number, listComp:ListBase):int 
      { 
       var p1 : Point; 
       var p2 : Point; 
       var renderer : DisplayObject; 

       for(var i:int=0; i<listComp.dataProvider.length; i++) { 
        renderer = DisplayObject(listComp.indexToItemRenderer(i)); 
        if (!renderer) //item is not displayed (scroll to view it) 
         continue; 
        p1 = new Point(renderer.x, renderer.y); 
        p2 = new Point(renderer.width, renderer.height); 
        p1 = renderer.parent.localToGlobal(p1); 
        p2 = renderer.localToGlobal(p2); 
        if(globalX >= p1.x && globalX <= p2.x && globalY >= p1.y && globalY <= p2.y) 
         return i; 
       } 
       return -1; 
      } 

     ]]> 
    </mx:Script> 
</mx:Application> 
2

Вы можете сделать две вещи:

  1. Вы можете отключить элементы в списке, которые не перетаскивать, основанные на собственности на объект данных, который SelectedItem в. Это приведет к тому, что они будут визуально отключены, что вы, возможно, не захотите, так что вы также можете попробовать ...

  2. Вы можете установить свойство dragEnabled списка «true», когда действительные элементы (на основе данных выбранного элемента объект) и «false», когда элементы недействительны.

+0

Хорошие варианты Robusto, вы использовали/протестировали любой из них? 1 кажется довольно надежным, но визуально раздражающим. 2 похоже, что это сработает, но многие вещи, которые кажутся им, должны работать для меня. – invertedSpear

+0

Я использовал их оба, и они работают для моей компании. Обратите внимание, что # 1 использует свойство disabledFunction List, а # 2 вызывает обработчик из события dragDrop, который проверяет, действительна ли строка для перетаскивания, и если это НЕ допустимые вызовы event.stopImmediatePropagation() и event.preventDefault() , – Robusto

3

Если то, что вы хотите, чтобы избежать перетаскивания элемента, который вы должны использовать что-то вроде этого:

<fx:Script> 
    <![CDATA[ 
     private function onDragStart(event:DragEvent):void { 
     var selectedNode:Object = itemsList.selectedItem; 
     if (selectedNode is not a draggable item) { 
      event.stopImmediatePropagation(); 
     } 
    } 
    ]]> 
</fx:Script> 

<s:List id="itemsList" dragStart="onDragStart(event)"/> 

Событие DragStart отправляется сразу, когда начинается перетаскивание, поэтому, если вы остановите распространение события, вы избегаете перетаскивания элемента.

Смежные вопросы