java align=left> 工作台窗口的Editor区域默认是显示的,而且它支持拖拽操作。
在Eclipse里面,把一个文件拖到Editor区域,就会自动打开该文件的Editor.该特性是在IWorkbenchWindowConfigurer 中设置。
在Password Gate中,当拖动Password Gate View中的一个Group 或者 Service到Editor区域,会在Editor显示该项的属性。
要实现此特性,有四部分是必须的。
1 实现必要的Transfer类型,而且定义Editor要支持哪些类型。在Password Gate中,Transfer是LocalSelectionTransfer.Transfer用来进行数据的序列化,它可以支持在同一个程序,或不同程序间拖拽。
2 因为在拖拽传递的过程中Editor Input 要实现序列化,所以要实现IPersistableElement接口。
3 加入一个释放适配器,当一个元素被扔到Editor区域,它可以知道如何进行操作,其实就是打开该元素的Editor.
4 使Password View能够进行拖操作,它要提供供拖的元素。
下面进行代码实现。
在RCP的WorkbenchWindowAdvisor. preWindowOpen中定义要求Editor Area支持的拖入对象的类型,以及打开相应Editor的事件。
ApplicationWorkbenchWindowAdvisor.preWindowOpen()
01 public void preWindowOpen() { 02 ...... 03 configurer.addEditorAreaTransfer(LocalSelectionTransfer.getInstance()); 04 configurer.configureEditorAreaDropListener(new EditorAreaDropAdapter( 05 configurer.getWindow())); 06 } |
MILY: Arial; mso-fareast-font-family: 宋体; mso-font-kerning: 1.0pt; mso-ansi-language: EN-US; mso-fareast-language: ZH-CN; mso-bidi-language: AR-SA">
Row 03定义了Editor Area支持的Transfer为LocalSelectionTransfer, LocalSelectionTransfer为自己实现的传输介质类。Row 04定义了对拖入Editor Area的对象的处理方法。EditorAreaDropAdapter实现了DropTargetListener接口,用来监听Editor Area中的Drop事件,它会打开拖入Editor Area的对象所对应的Editor,如果同时拖入多个对象,它会打开每个对象对应的Editor.
EditorAreaDropAdapter.java |
01 public class EditorAreaDropAdapter extends DropTargetAdapter { 02 private IWorkbenchWindow window; 03 04 public EditorAreaDropAdapter(IWorkbenchWindow window) { 05 this.window = window; 06 } 07 08 public void dragEnter(DropTargetEvent event) { 09 // always indicate a copy 10 event.detail = DND.DROP_COPY; 11 } 12 13 public void dragOperationChanged(DropTargetEvent event) { 14 // always indicate a copy 15 event.detail = DND.DROP_COPY; 16 } 17 18 public void drop(final DropTargetEvent event) { 19 Display d = window.getShell().getDisplay(); 20 final IWorkbenchPage page = window.getActivePage(); 21 if (page != null) { 22 d.asyncExec(new Runnable() { 23 public void run() { 24 asyncDrop(event, page); 25 } 26 }); 27 } 28 } 29 30 private void asyncDrop(DropTargetEvent event, IWorkbenchPage page) { 31 if (LocalSelectionTransfer.getInstance().isSupportedType( 32 event.currentDataType)) { 33 StructuredSelection selection = (StructuredSelection) event.data; 34 for (Iterator iter = selection.iterator(); iter.hasNext();) { 35 Object o = iter.next(); 36 if (o instanceof Record) { 37 IEditorInput input = new RecordEditorInput((Record) o); 38 try { 39 page.openEditor(input, RecordEditor.ID); 40 } catch (Exception e) { 41 PwdgatePlugin.log("open ediotr RecordEditor", e); 42 } 43 } else if (o instanceof Group) { 44 IEditorInput input = new GroupEditorInput((Group) o); 45 try { 46 page.openEditor(input, GroupEditor.ID); 47 } catch (PartInitException e) { 48 PwdgatePlugin.log("open ediotr GroupEditor", e); 49 } 50 } 51 } 52 } 53 } 54 } |
Row 18,用来处理Drop事件,Row 30的asyncDrop()方法用来打来相应对象的Editor.
现在Editor Area已经可以接收拖入对象了。下一步要使一个View支持拖出对象的功能。下面的例子是在Pass Gate View中的createPartControl()方法中为一个TreeViewer添加拖出功能。
PassGateView.java |
01 private void initDragAndDrop() { 02 Transfer[] transfer = new Transfer[] { LocalSelectionTransfer 03 .getInstance() }; 04 LocalSelectionDragAdapter adapter = new LocalSelectionDragAdapter( 05 viewer); 06 viewer.addDragSupport(DND.DROP_MOVE | DND.DROP_COPY, transfer, adapter); 07 08 LocalSelectionDropAdapter dropAdapter = new LocalSelectionDropAdapter( 09 viewer); 10 viewer.addDropSupport(DND.DROP_MOVE | DND.DROP_COPY, transfer, 11 dropAdapter); 12 } |
Row 06 为TreeViewer添加了监听拖动的事件,当在TreeViewer中有拖动时,LocalSelectionDragAdapter把拖动的对象放入LocalSelectionTransfer中,通过其传到 Editor Area中。
LocalSelectionDragAdapter.java |
01 public class LocalSelectionDragAdapter extends DragSourceAdapter { 02 03 ISelectionProvider selectionProvider; 04 05 public LocalSelectionDragAdapter(ISelectionProvider provider) { 06 selectionProvider = provider; 07 } 08 09 public void dragFinished(DragSourceEvent event) { 10 // TODO Auto-generated method stub 11 super.dragFinished(event); 12 System.out 13 .println("DragSourceListener.dragFinished(DragSourceEvent event)"); 14 } 15 16 public void dragSetData(DragSourceEvent event) { 17 System.out 18 .println("DragSourceListener.dragSetData(DragSourceEvent event)"); 19 DragSource dragSource = (DragSource) event.widget; 20 Control control = dragSource.getControl(); 21 if (control != control.getDisplay().getFocusControl()) { 22 event.doit = false; 23 return; 24 } 25 26 IStructuredSelection selection = (IStructuredSelection) selectionProvider 27 .getSelection(); 28 29 if (selection.isEmpty()) { 30 event.doit = false; 31 return; 32 } 33 LocalSelectionTransfer.getInstance().setSelection(selection); 34 event.doit = true; 35 } 36 37 public void dragStart(DragSourceEvent event) { 38 System.out 39 .println("DragSourceListener.dragStart(DragSourceEvent event)"); 40 } 41 } |