一旦我调用了DragManager.acceptDrag,有什么办法可以"不接受"拖拽吗?假设我有一个可以接受拖放的视图,但仅限于某些区域。一旦用户拖过这些区域之一,我就会调用 DragManager.acceptDrag(this) (来自 DragEvent.DRAG_OVER 处理程序),但是如果用户随后移出该区域,我想将拖动的状态更改为不接受并显示DragManager.NONE 反馈。但是,调用 DragManager.acceptDrag(null) 和 DragManager.showFeedback(DragManager.NONE) 似乎都没有任何效果。一旦我接受了拖动设置反馈类型,我似乎无法更改它。
明确一点:用户应该能够放置的区域不是组件,甚至不是显示对象,实际上它们只是文本字段文本中的范围(如选择)。如果他们是他们自己的组件,我可以通过让他们每个人单独接受拖动事件来解决它。我想我可以创建浮动在文本上的代理组件来模拟它,但如果没有必要,我宁愿不这样做。
我现在已经设法让它在 AIR 和浏览器中运行,但只能通过将代理组件放在应该能够放置内容的文本范围的顶部。这样我就可以得到正确的反馈,并且在拖动退出时会自动不接受放置。
这是D最奇怪的地方
您是否只使用了dragEnter 方法?如果您尝试拒绝拖动,同时仍拖动同一组件,则需要同时使用 dragEnter 和 dragOver 方法。
看看这个例子:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
| ?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 |
你误解了这个概念。您的"不接受"是通过实现 dragOverHandler 并发出不需要数据的信号来实现的。
这是基本概念:
注册dragEnterHandler或者覆盖已经注册的方法。
1 2 3 4
| function dragEnterHandler(event: DragEvent):void {
if (data suites at least one location in this component)
DragManager.acceptDragDrop(this);
} |
这使您的容器能够接收更多消息(dragOver/dragExit)。但这不是决定应该显示哪种鼠标光标的位置。
没有 DragManager.acceptDragDrop(this);不会调用其他处理程序。
注册dragOverHandler或者覆盖已经注册的方法。
1 2 3 4 5 6 7 8
| 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
} |
调用 DragManager.showFeedback(DragManager.NONE);显示"不接受"的诀窍。
注册dragExitHandler或者覆盖已经注册的方法。
1 2 3
| function dragOverHandler(event: DragEvent):void {
// handle the recieved data as you like.
} |
如果您不需要在 AIR 中进行原生拖放,则可以通过子类化 WindowedApplication 并设置 DragManager 来获得 Flex 拖放行为。有关更多信息,请参阅 Adob??e Jira 上的此帖子:https://bugs.adobe.com/jira/browse/SDK-13983
是的,拖放在 AIR 中是不同的。我讨厌那个!要想弄清楚如何让事情像在 flex 中构建的自定义 dnd 一样工作,需要花费很多时间。
至于坐标,可以使用 localToContent 和 localToGlobal 方法。它们可能有助于将坐标转换为有用的东西。
祝你好运。如果我想到其他任何事情,我会告诉你。
好的,我现在看到了问题。尝试将其设置为 dragInitiator.
而不是 null
看看这个。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42
| ?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 |