package leaf.ui; import info.clearthought.layout.TableLayout; import info.clearthought.layout.TableLayoutConstraints; import java.awt.Dimension; import java.awt.GraphicsEnvironment; import java.awt.Insets; import java.awt.Rectangle; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.util.Enumeration; import java.util.LinkedList; import java.util.List; import javax.swing.JButton; import javax.swing.JLabel; import javax.swing.JScrollPane; import javax.swing.JTree; import javax.swing.event.TreeSelectionEvent; import javax.swing.event.TreeSelectionListener; import javax.swing.tree.DefaultMutableTreeNode; import javax.swing.tree.DefaultTreeModel; import javax.swing.tree.TreePath; import javax.swing.tree.TreeSelectionModel; import com.evolute.swing.dialog.EvoDialog; import com.evolute.utils.error.ErrorLogger; import com.evolute.utils.images.ImageException; import com.evolute.utils.images.ImageIconLoader; import com.evolute.utils.ui.trees.TreeTools; public class TreeInserterDialog extends EvoDialog { private static final long serialVersionUID = 1L; private static final Dimension DIALOG_DEFAULT_DIMENSIONS = new Dimension( 800, 500 ); private static final String ICON_NAME_ADD = "leaf/ui/icons/add.png"; private static final String ICON_NAME_REM = "leaf/ui/icons/rem.png"; private final DefaultMutableTreeNode newRoot = new DefaultMutableTreeNode(); private final DefaultTreeModel newModel = new DefaultTreeModel( newRoot ); private final JTree newTree = new JTree( newModel ); private final JScrollPane newScroll = new JScrollPane( newTree ); private final DefaultMutableTreeNode allRoot; private final DefaultTreeModel allModel; private final JTree allTree; private final JScrollPane allScroll; private JButton buttonAdd = null; private JButton buttonRemove = null; private final JButton buttonOK = new JButton( "OK" ); private final JButton buttonCancel = new JButton( "Cancelar" ); private static List expandedNodes = new LinkedList(); public TreeInserterDialog( String title, DefaultMutableTreeNode root ) { this.allRoot = root; this.allModel = new DefaultTreeModel( allRoot ); this.allTree = new JTree( allModel ); this.allScroll = new JScrollPane( allTree ); this.setTitle( title ); try { buttonAdd = new JButton( ImageIconLoader.loadImageIcon( ICON_NAME_ADD ) ); buttonRemove = new JButton( ImageIconLoader.loadImageIcon( ICON_NAME_REM ) ); } catch( ImageException e ) { ErrorLogger.logException( e ); } startupComponents(); setupLayout(); placeComponents(); startupListeners(); loadExpansionState(); setEnabled(); final Rectangle rect = GraphicsEnvironment.getLocalGraphicsEnvironment().getMaximumWindowBounds(); this.setSize( rect.width, rect.height ); // this.setSize( DIALOG_DEFAULT_DIMENSIONS ); this.setModal( true ); this.setVisible( true ); } private void loadExpansionState() { TreeTools.refreshTree( allTree, allRoot, expandedNodes.isEmpty() ); for( Object userObject : expandedNodes ) { TreeTools.expandNodeForObject( userObject, allTree ); } } private void startupComponents() { newTree.setRootVisible( false ); newTree.getSelectionModel().setSelectionMode( TreeSelectionModel.DISCONTIGUOUS_TREE_SELECTION ); allTree.setRootVisible( false ); allTree.getSelectionModel().setSelectionMode( TreeSelectionModel.DISCONTIGUOUS_TREE_SELECTION); allScroll.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_ALWAYS ); allScroll.setHorizontalScrollBarPolicy( JScrollPane.HORIZONTAL_SCROLLBAR_NEVER ); newScroll.setVerticalScrollBarPolicy( JScrollPane.VERTICAL_SCROLLBAR_ALWAYS ); newScroll.setHorizontalScrollBarPolicy( JScrollPane.HORIZONTAL_SCROLLBAR_NEVER ); buttonAdd.setToolTipText( "Adicionar" ); buttonRemove.setToolTipText( "Remover" ); buttonAdd.setMargin( new Insets(0,0,0,0) ); buttonRemove.setMargin( new Insets(0,0,0,0) ); } private void setupLayout() { TableLayout layout = new TableLayout( new double[]{ TableLayout.FILL, TableLayout.MINIMUM, TableLayout.FILL, TableLayout.MINIMUM, TableLayout.MINIMUM }, new double[]{ TableLayout.MINIMUM, TableLayout.MINIMUM, TableLayout.FILL, TableLayout.MINIMUM, TableLayout.MINIMUM } ); layout.setHGap( 5 ); layout.setVGap( 5 ); getContentPane().setLayout( layout ); } private void placeComponents() { getContentPane().add( new JLabel("Todos"), new TableLayoutConstraints( 0,0 ) ); getContentPane().add( new JLabel("a adicionar..."), new TableLayoutConstraints( 2,0,4,0 ) ); getContentPane().add( allScroll, new TableLayoutConstraints( 0,1,0,4 ) ); getContentPane().add( buttonAdd, new TableLayoutConstraints( 1,1 ) ); getContentPane().add( buttonRemove, new TableLayoutConstraints( 1,3 ) ); getContentPane().add( newScroll, new TableLayoutConstraints( 2,1,4,3 ) ); getContentPane().add( buttonOK, new TableLayoutConstraints( 3,4 ) ); getContentPane().add( buttonCancel, new TableLayoutConstraints( 4,4 ) ); } private void startupListeners() { buttonAdd.addActionListener( new ActionListener() { @Override public void actionPerformed( ActionEvent e ) { move( allTree, newTree ); } } ); buttonRemove.addActionListener( new ActionListener() { @Override public void actionPerformed( ActionEvent e ) { move( newTree, allTree ); } } ); buttonOK.addActionListener( new ActionListener() { @Override public void actionPerformed( ActionEvent e ) { ok(); } } ); buttonCancel.addActionListener( new ActionListener() { @Override public void actionPerformed( ActionEvent e ) { cancel(); } } ); allTree.getSelectionModel().addTreeSelectionListener( new TreeSelectionListener(){ @Override public void valueChanged( TreeSelectionEvent e ) { setEnabled(); } } ); newTree.getSelectionModel().addTreeSelectionListener( new TreeSelectionListener(){ @Override public void valueChanged( TreeSelectionEvent e ) { setEnabled(); } } ); } private void move( JTree from, JTree to ) { TreePath [] paths = from.getSelectionPaths(); if( paths != null ) { DefaultMutableTreeNode fromRoot = (DefaultMutableTreeNode) from.getModel().getRoot(); DefaultMutableTreeNode toRoot = (DefaultMutableTreeNode) to.getModel().getRoot(); for( TreePath path : paths ) { for( int i = 1; i < path.getPathCount(); ++i ) { DefaultMutableTreeNode node = (DefaultMutableTreeNode) path.getPathComponent( i ); DefaultMutableTreeNode parent = (DefaultMutableTreeNode) path.getPathComponent( i-1 ); if( node != null && parent != null ) { DefaultMutableTreeNode exists = TreeTools.findNodeWithUserObject( node.getUserObject(), toRoot ); if( exists == null ) { add(node, parent.getUserObject(), toRoot, path.getPathCount() == i + 1 ); } else if( i + 1 == path.getPathCount() ) { TreeTools.merge( exists, node ); } } } removeNode( (DefaultMutableTreeNode) path.getLastPathComponent(), fromRoot ); } TreeTools.refreshTree( from, fromRoot, true ); TreeTools.refreshTree( to, toRoot, true ); } } private void removeNode( DefaultMutableTreeNode node, DefaultMutableTreeNode root ) { DefaultMutableTreeNode parent = (DefaultMutableTreeNode) node.getParent(); node.removeFromParent(); if( parent != null && parent.getChildCount() == 0 ) { removeNode( parent, root ); } } private void add( DefaultMutableTreeNode node, Object parent, DefaultMutableTreeNode where, boolean fullClone ) { DefaultMutableTreeNode parentNode = TreeTools.findNodeWithUserObject( parent, where ); if( parentNode == null ) { parentNode = where; } parentNode.add( fullClone ? TreeTools.cloneFullNode(node) : (DefaultMutableTreeNode) node.clone() ); } private void ok() { close(); } private void cancel() { newRoot.removeAllChildren(); close(); } private void close() { saveExpandedState(); setVisible( false ); } private void setEnabled() { boolean allSelected = allTree.getSelectionPath() != null; boolean newSelected = newTree.getSelectionPath() != null; boolean somethingToAdd = newRoot.getChildCount() > 0; buttonAdd.setEnabled( allSelected ); buttonRemove.setEnabled( newSelected ); buttonOK.setEnabled( somethingToAdd ); } public DefaultMutableTreeNode getResult() { return newRoot; } private void saveExpandedState( ) { expandedNodes.clear(); if( allTree != null ) { Object root = allTree.getModel().getRoot(); if( root != null ) { savePath( new TreePath(root) ); } } } private void savePath( TreePath treePath ) { if( treePath != null ) { Enumeration expanded = allTree.getExpandedDescendants(treePath); if( expanded != null ) { while( expanded.hasMoreElements() ) { TreePath path = expanded.nextElement(); if( path != null ) { Object leaf = path.getLastPathComponent(); if( leaf instanceof DefaultMutableTreeNode ) { Object userObject = ((DefaultMutableTreeNode)leaf).getUserObject(); if( userObject != null ) { expandedNodes.add(userObject); } } } savePath(path); } } } } }