2008-08-14 13 views
5

Một khi tôi đã gọi DragManager.acceptDrag là có cách nào để "không chấp nhận" kéo? Giả sử tôi có chế độ xem có thể chấp nhận kéo và thả, nhưng chỉ ở một số khu vực nhất định. Khi người dùng kéo qua một trong các khu vực này, tôi gọi DragManager.acceptDrag(this) (từ trình xử lý DragEvent.DRAG_OVER), nhưng nếu người dùng di chuyển ra khỏi khu vực này, tôi muốn thay đổi trạng thái của thao tác kéo thành không được chấp nhận và hiển thị phản hồi DragManager.NONE. Tuy nhiên, không gọi DragManager.acceptDrag(null) cũng không phải DragManager.showFeedback(DragManager.NONE) dường như có bất kỳ ảnh hưởng nào. Một khi tôi đã chấp nhận kéo một tập các loại phản hồi tôi dường như không thể thay đổi nó.Làm cách nào để "không chấp nhận" một lần kéo trong Flex?

Chỉ cần làm rõ: các khu vực mà người dùng có thể thả không phải là thành phần hoặc thậm chí hiển thị đối tượng, trên thực tế chúng chỉ nằm trong văn bản của trường văn bản (như vùng chọn). Nếu chúng là các thành phần của riêng chúng, tôi có thể giải quyết nó bằng cách làm cho mỗi thành phần của chúng chấp nhận các sự kiện kéo riêng lẻ. Tôi đoán tôi có thể tạo các thành phần proxy trôi nổi trên văn bản để mô phỏng nó, nhưng tôi không muốn nếu nó không cần thiết.


Tôi đã quản lý để làm việc trong cả AIR và trình duyệt ngay bây giờ, nhưng chỉ bằng cách đặt các thành phần proxy trên đầu phạm vi văn bản nơi bạn có thể thả mọi thứ. Bằng cách đó, tôi nhận được phản hồi và giọt thích hợp sẽ tự động không được chấp nhận khi kéo lối ra.

Đây là điều lạ lùng nhất về D & D trong AIR:

DragManager.doDrag(initiator, source, event, dragImage, offsetX, offsetY); 

Trong Flex dựa trên trình duyệt, offsetXoffsetY nên tiêu cực (để nói rằng tài liệu, và nó hoạt động tốt). Tuy nhiên, khi chạy chính xác cùng mã trong AIR, bạn phải thực hiện bù trừ tích cực. Những con số tương tự, nhưng tích cực. Điều đó rất, rất kỳ lạ.


Tôi đã thử nghiệm một số chi tiết và những gì @maclema hoạt động, nhưng không phải nếu bạn chạy trong AIR. Dường như việc kéo và thả AIR là khác nhau. Nó thực sự, thực sự kỳ lạ vì không chỉ là thông tin phản hồi không hiển thị chính xác, và nó không thể không chấp nhận, nhưng các tọa độ cũng hoàn toàn tắt. Tôi vừa thử ứng dụng của mình trong trình duyệt thay vì AIR và kéo và thả hoàn toàn bị hỏng.

Ngoài ra, bỏ qua trình xử lý dragEnter hoạt động tốt trong AIR, nhưng phá vỡ mọi thứ khi chạy trong trình duyệt.

Trả lời

6

Bạn chỉ sử dụng phương thức kéoEnter? Nếu bạn đang cố gắng từ chối kéo trong khi vẫn kéo trên cùng một thành phần, bạn cần sử dụng cả hai phương thức kéo và kéo.

Kiểm tra ví dụ này:

<?xml version="1.0" encoding="utf-8"?> 
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute"> 
    <mx:Script> 
     <![CDATA[ 
      import mx.core.DragSource; 
      import mx.managers.DragManager; 
      import mx.events.DragEvent; 

      private function onDragEnter(e:DragEvent):void { 
       if (e.target == lbl) { 

        if (e.localX < lbl.width/2) { 
         trace("accept"); 
         DragManager.acceptDragDrop(this); 
        } 
        else { 
         DragManager.acceptDragDrop(null); 
        } 
       } 
      } 

      private function doStartDrag(e:MouseEvent):void { 
       if (e.buttonDown) { 
        var ds:DragSource = new DragSource(); 
        ds.addData("test", "text"); 

        DragManager.doDrag(btn, ds, e); 
       } 
      } 
     ]]> 
    </mx:Script> 
    <mx:Label id="lbl" text="hello world!" left="10" top="10" dragEnter="onDragEnter(event)" dragOver="onDragEnter(event)" /> 
    <mx:Button id="btn" x="47" y="255" label="Button" mouseMove="doStartDrag(event)"/> 
</mx:Application> 
+0

Chấp nhận kéo trong trình xử lý 'DRAG_ENTER' làm mọi thứ trở nên tồi tệ hơn. Tôi vẫn không thể từ chối việc kéo (gọi 'DragManager.acceptDragDrop (null)' không có hiệu lực, ít nhất là không có hiệu ứng có thể nhìn thấy), và chấp nhận kéo trên nhập loại bỏ điều khiển nhỏ mà tôi có. Bây giờ dấu + bên dưới con trỏ được hiển thị ngay khi chuột vào thành phần, thay vì bắt đầu hiển thị khi người dùng kéo qua các vùng đặc biệt. – Theo

+0

tốt, điều đó cũng sẽ làm cho người khởi tạo trở thành một mục tiêu, hiển thị dấu + khi người dùng kéo qua thành phần đó (mà nó chắc chắn không nên vì nó không chấp nhận các giọt). Vì vậy, điều đó không hoạt động. – Theo

0

ok, tôi thấy vấn đề bây giờ. Thay vì null, hãy thử đặt nó vào dragInitiator.

Kiểm tra điều này.

<?xml version="1.0" encoding="utf-8"?> 
<mx:WindowedApplication xmlns:mx="http://www.adobe.com/2006/mxml" layout="absolute"> 
    <mx:Script> 
     <![CDATA[ 
      import mx.controls.Alert; 
      import mx.events.DragEvent; 
      import mx.managers.DragManager; 
      import mx.core.DragSource; 

      private function doStartDrag(e:MouseEvent):void { 
       if (e.buttonDown && !DragManager.isDragging) { 
       var ds:DragSource = new DragSource(); 
       ds.addData("test", "test"); 

       DragManager.doDrag(btn, ds, e); 
       } 
      } 

      private function handleDragOver(e:DragEvent):void { 
       if (e.localX < cvs.width/2) { 
        //since null does nothing, lets just set to accept the drag 
        //operation, but accept it to the dragInitiator 
        DragManager.acceptDragDrop(e.dragInitiator); 
       } 
       else { 
        //accept drag 
        DragManager.acceptDragDrop(cvs); 
        DragManager.showFeedback(DragManager.COPY); 
       } 
      } 

      private function handleDragDrop(e:DragEvent):void { 
       if (e.dragSource.hasFormat("test")) { 
        Alert.show("Got a drag drop!"); 
       } 
      } 
     ]]> 
    </mx:Script> 
    <mx:Canvas x="265" y="66" width="321" height="245" backgroundColor="#FF0000" id="cvs" dragOver="handleDragOver(event)" dragDrop="handleDragDrop(event)"> 
    </mx:Canvas> 
    <mx:Button id="btn" x="82" y="140" label="Drag Me" mouseDown="doStartDrag(event)"/> 
</mx:WindowedApplication> 
0

Có, kéo và thả khác với AIR. Tôi ghét điều đó! Phải mất rất nhiều thời gian để tìm hiểu làm thế nào để có được những thứ để làm việc giống như dnd tùy chỉnh được xây dựng trong flex.

Đối với các tọa độ, có thể chơi xung quanh với phương thức localToContent và localToGlobal. Họ có thể giúp đỡ trong việc dịch các tọa độ để một cái gì đó hữu ích.

Chúc may mắn. Tôi sẽ cho bạn biết nếu tôi nghĩ về bất cứ điều gì khác.

1

Nếu bạn không cần kéo và thả bản địa trong AIR, bạn có thể nhận hành vi kéo và thả Flex bằng cách phân lớp WindowedApplication và thiết lập DragManager. Xem bài đăng này trên Adobe Jira để biết thêm thông tin: https://bugs.adobe.com/jira/browse/SDK-13983

1

Bạn hiểu nhầm khái niệm. Không thể chấp nhận "unaccept" của bạn bằng cách triển khai pullOverHandler và báo hiệu rằng dữ liệu không được mong muốn.

Dưới đây là khái niệm cơ bản:

  1. đăng ký dragEnterHandler hoặc ghi đè lên các phương pháp đã đăng ký.

    function dragEnterHandler(event: DragEvent):void { 
        if (data suites at least one location in this component) 
         DragManager.acceptDragDrop(this); 
    } 
    

    Điều này cho phép vùng chứa của bạn nhận thêm thông báo (dragOver/dragExit). Nhưng đây là KHÔNG vị trí để quyết định loại con trỏ chuột nào sẽ được hiển thị.

    Nếu không có DragManager.acceptDragDrop (điều này); các trình xử lý khác không được gọi.

  2. đăng ký dragOverHandler hoặc ghi đè phương thức đã đăng ký.

    function dragOverHandler(event: DragEvent):void { 
        if (data suites at least no location in this component) { 
         DragManager.showFeedback(DragManager.NONE); 
         return; 
        } 
    
        ... // handle other cases and show the cursor/icon you want 
    } 
    

    Gọi DragManager.showFeedback (DragManager.NONE); thực hiện thủ thuật để hiển thị "không được chấp nhận".

  3. đăng ký kéoExitHandler hoặc ghi đè phương thức đã đăng ký.

    function dragOverHandler(event: DragEvent):void { 
        // handle the recieved data as you like. 
    }