SWT 应用程序:可拖动选项卡是否可行?
SWT Application: Are Draggable Tabs Possible?
我正在使用 SWT 构建一个 Java 应用程序。该应用程序的要求之一是它有多个windows。与其拥有 "forever independent" windows,我认为实现一个功能会很酷,就像在大多数浏览器中那样,您有一个单一的表格 window,其中每个选项卡都可以被拖出以创建一个单独的window。在使用 Google 进行一些研究后,似乎可以实现此 using JavaFX,但是是否有可能(并且相对容易)在 SWT 中实现相同的功能?提前致谢。
虽然我的看法可能有点晚了,但还是在这里。下面的代码片段是一个粗略的 POC,它允许从 CTabFolder
中拖动项目,当项目被放到文件夹边界之外时,会打开一个 shell 以显示项目的内容。
public static void main( String[] args ) {
Display display = new Display();
final Shell shell = new Shell( display );
shell.setLayout( new FillLayout() );
final CTabFolder folder = new CTabFolder( shell, SWT.BORDER );
for( int i = 0; i < 4; i++ ) {
CTabItem item = new CTabItem( folder, SWT.CLOSE );
item.setText( "Item " + i );
Text text = new Text( folder, SWT.MULTI );
text.setText( "Content for Item " + i );
item.setControl( text );
}
Listener dragListener = new Listener() {
private CTabItem dragItem;
public void handleEvent( Event event ) {
Point mouseLocation = new Point( event.x, event.y );
switch( event.type ) {
case SWT.DragDetect: {
CTabItem item = folder.getItem( mouseLocation );
if( dragItem == null && item != null ) {
dragItem = item;
folder.setCapture( true );
}
break;
}
case SWT.MouseUp: {
if( dragItem != null && !folder.getBounds().contains( mouseLocation ) ) {
popOut( dragItem, folder.toDisplay( mouseLocation ) );
dragItem.dispose();
dragItem = null;
}
break;
}
}
}
};
folder.addListener( SWT.DragDetect, dragListener );
folder.addListener( SWT.MouseUp, dragListener );
shell.pack();
shell.open();
while( !shell.isDisposed() ) {
if( !display.readAndDispatch() )
display.sleep();
}
display.dispose();
}
private static void popOut( CTabItem tabItem, Point location ) {
Control control = tabItem.getControl();
tabItem.setControl( null );
Shell itemShell = new Shell( tabItem.getParent().getShell(), SWT.DIALOG_TRIM | SWT.RESIZE );
itemShell.setLayout( new FillLayout() );
control.setParent( itemShell );
control.setVisible( true ); // control is hidden by tabItem.setControl( null ), make visible again
itemShell.pack();
itemShell.setLocation( location );
itemShell.open();
}
虽然此示例使用 CTabFolder
,但也应该可以使用(本地)TabFolder
。
当然缺少的是拖动项目时的视觉反馈和中止拖动操作的方法(例如 Esc 键),可能还有更多东西...
我正在使用 SWT 构建一个 Java 应用程序。该应用程序的要求之一是它有多个windows。与其拥有 "forever independent" windows,我认为实现一个功能会很酷,就像在大多数浏览器中那样,您有一个单一的表格 window,其中每个选项卡都可以被拖出以创建一个单独的window。在使用 Google 进行一些研究后,似乎可以实现此 using JavaFX,但是是否有可能(并且相对容易)在 SWT 中实现相同的功能?提前致谢。
虽然我的看法可能有点晚了,但还是在这里。下面的代码片段是一个粗略的 POC,它允许从 CTabFolder
中拖动项目,当项目被放到文件夹边界之外时,会打开一个 shell 以显示项目的内容。
public static void main( String[] args ) {
Display display = new Display();
final Shell shell = new Shell( display );
shell.setLayout( new FillLayout() );
final CTabFolder folder = new CTabFolder( shell, SWT.BORDER );
for( int i = 0; i < 4; i++ ) {
CTabItem item = new CTabItem( folder, SWT.CLOSE );
item.setText( "Item " + i );
Text text = new Text( folder, SWT.MULTI );
text.setText( "Content for Item " + i );
item.setControl( text );
}
Listener dragListener = new Listener() {
private CTabItem dragItem;
public void handleEvent( Event event ) {
Point mouseLocation = new Point( event.x, event.y );
switch( event.type ) {
case SWT.DragDetect: {
CTabItem item = folder.getItem( mouseLocation );
if( dragItem == null && item != null ) {
dragItem = item;
folder.setCapture( true );
}
break;
}
case SWT.MouseUp: {
if( dragItem != null && !folder.getBounds().contains( mouseLocation ) ) {
popOut( dragItem, folder.toDisplay( mouseLocation ) );
dragItem.dispose();
dragItem = null;
}
break;
}
}
}
};
folder.addListener( SWT.DragDetect, dragListener );
folder.addListener( SWT.MouseUp, dragListener );
shell.pack();
shell.open();
while( !shell.isDisposed() ) {
if( !display.readAndDispatch() )
display.sleep();
}
display.dispose();
}
private static void popOut( CTabItem tabItem, Point location ) {
Control control = tabItem.getControl();
tabItem.setControl( null );
Shell itemShell = new Shell( tabItem.getParent().getShell(), SWT.DIALOG_TRIM | SWT.RESIZE );
itemShell.setLayout( new FillLayout() );
control.setParent( itemShell );
control.setVisible( true ); // control is hidden by tabItem.setControl( null ), make visible again
itemShell.pack();
itemShell.setLocation( location );
itemShell.open();
}
虽然此示例使用 CTabFolder
,但也应该可以使用(本地)TabFolder
。
当然缺少的是拖动项目时的视觉反馈和中止拖动操作的方法(例如 Esc 键),可能还有更多东西...