package gui;
import java.awt.LayoutManager;
import javax.swing.ImageIcon;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.JPopupMenu;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTree;
import javax.swing.ListSelectionModel;
import javax.swing.event.TreeSelectionEvent;
import javax.swing.event.TreeSelectionListener;
import javax.swing.table.AbstractTableModel;
import javax.swing.tree.DefaultMutableTreeNode;
import javax.swing.tree.DefaultTreeModel;
import javax.swing.tree.TreeCellRenderer;
import javax.swing.tree.TreePath;
import javax.swing.tree.TreeSelectionModel;
import java.awt.Cursor;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.datatransfer.DataFlavor;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.dnd.DnDConstants;
import java.awt.dnd.DragGestureEvent;
import java.awt.dnd.DragGestureListener;
import java.awt.dnd.DragGestureRecognizer;
import java.awt.dnd.DragSource;
import java.awt.dnd.DragSourceDragEvent;
import java.awt.dnd.DragSourceDropEvent;
import java.awt.dnd.DragSourceEvent;
import java.awt.dnd.DragSourceListener;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import dao.Controller;
import dao.ISweaveTag;
import dao.IViewport;
import dao.IViewportPlot;
import dao.RObject;
import dao.RObjectViewportPlot;
import dao.RObjectViewportTable;
import dao.TransferableSweaveTag;
import gui.DataTableModel;
import helper.Helper;
import helper.Constants;
public class JRObjectTreePane extends JPanel implements TreeSelectionListener {
/**
*
*/
private static final long serialVersionUID = -3717419818700367818L;
private static JTree tree;
private static DefaultMutableTreeNode dataFilesNode;
private static DefaultMutableTreeNode tablesNode;
private static DefaultMutableTreeNode plotsNode;
private TreeDragSource ds;
protected JMenuItem menuItemShow;
protected JMenuItem menuItemRemove;
protected JMenuItem menuItemDeattach;
private JMenuItem menuItemEval;
private JMenuItem menuItemRemovefromR;
private JMenuItem menuItemtoLatex;
private JMenuItem menuItemRemovefromLatex;
private JMenuItem menuItemGotoSwt;
public JRObjectTreePane() {
super(new GridLayout(1, 0));
DefaultMutableTreeNode top = new DefaultMutableTreeNode("Object-Manager");
// Create a tree that allows one selection at a time.
tree = new JTree(top);
tree.setRowHeight(32);
tree.setFont(new Font("Default", Font.PLAIN, 16));
tree.setCellRenderer(new JRObjectTreeCellRenderer());
createNodes(top);
tree.getSelectionModel().setSelectionMode(
TreeSelectionModel.DISCONTIGUOUS_TREE_SELECTION);
tree.setRootVisible(false);
tree.setShowsRootHandles(true);
ds = new TreeDragSource(tree, DnDConstants.ACTION_COPY);
// Create the scroll pane and add the tree to it.
JScrollPane treeView = new JScrollPane(tree);
createPopupMenu();
// Add the scroll pane to this panel.
add(treeView);
refresh();
}
public void valueChanged(TreeSelectionEvent e) {
DefaultMutableTreeNode node = (DefaultMutableTreeNode)
tree.getLastSelectedPathComponent();
if (node == null) {
return;
}
Object nodeInfo = node.getUserObject();
if (node.isLeaf()) {// TODO: Add some handling
} else {// TODO: Add some handling
}
}
private void createNodes(DefaultMutableTreeNode top) {
dataFilesNode = new DefaultMutableTreeNode("Data files");
top.add(dataFilesNode);
tablesNode = new DefaultMutableTreeNode("Tables");
top.add(tablesNode);
plotsNode = new DefaultMutableTreeNode("Plots");
top.add(plotsNode);
}
public static ArrayList getExpandedPaths() {
ArrayList expandedPaths = new ArrayList();
Enumeration enum0 = tree.getExpandedDescendants(tree.getPathForRow(0));
while(enum0 != null && enum0.hasMoreElements()) {
TreePath tp = (TreePath)enum0.nextElement();
expandedPaths.add(tp);
}
return expandedPaths;
}
public static void expandPaths(ArrayList pathlist) {
for(int i = 0; i < pathlist.size(); i++) {
tree.expandPath((TreePath)pathlist.get(i));
}
}
public static void addDataFile(IViewport ro) {
DefaultMutableTreeNode dmtn = new DefaultMutableTreeNode(ro);
getDataFilesNode().add(dmtn);
refresh();
}
public static void addTable(IViewport ro) {
getTablesNode().add(new DefaultMutableTreeNode(ro));
refresh();
}
public static void addPlot(IViewportPlot rpo) {
getPlotsNode().add(new DefaultMutableTreeNode(rpo));
refresh();
}
public static boolean removeObj(Object obj, DefaultMutableTreeNode from) {
if (from.getChildCount() == 0) {
return false;
}
for (from.children(); from.children().hasMoreElements();) {
DefaultMutableTreeNode node = (DefaultMutableTreeNode) from.children().nextElement();
if (obj.equals(node.getUserObject())) {
node.removeFromParent();
}
refresh();
return true;
}
return false;
}
public static boolean removeDataFile(RObjectViewportTable varname) {
return removeObj(varname, dataFilesNode);
}
public static boolean removeTable(RObjectViewportTable varname) {
return removeObj(varname, tablesNode);
}
public static boolean removePlot(IViewportPlot varname) {
return removeObj(varname, plotsNode);
}
public static void refresh() {
ArrayList expandedPaths = getExpandedPaths();
((DefaultTreeModel) tree.getModel()).reload();
expandPaths(expandedPaths);
}
public static DefaultMutableTreeNode getDataFilesNode() {
return dataFilesNode;
}
public static DefaultMutableTreeNode getPlotsNode() {
return plotsNode;
}
public static DefaultMutableTreeNode getTablesNode() {
return tablesNode;
}
private void createPopupMenu() {
// Create the popup menu.
JPopupMenu popup = new JPopupMenu();
menuItemShow = new JMenuItem("show");
menuItemShow.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
showActionPerformed(evt);
}
});
menuItemShow.setIcon(new ImageIcon("./images/i16x16/table.png"));
popup.add(menuItemShow);
popup.addSeparator();
menuItemGotoSwt = new JMenuItem("go to Sweave-Tag");
menuItemGotoSwt.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
gotoSwtActionPerformed(evt);
}
});
menuItemGotoSwt.setIcon(new ImageIcon("./images/i16x16/tex.png"));
popup.add(menuItemGotoSwt);
menuItemEval = new JMenuItem("evaluate");
menuItemEval.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
evalActionPerformed(evt);
}
});
menuItemEval.setIcon(new ImageIcon("./images/i16x16/eval.png"));
popup.add(menuItemEval);
menuItemtoLatex = new JMenuItem("insert Sweave-Tag");
menuItemtoLatex.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
toLatexActionPerformed(evt);
}
});
menuItemtoLatex.setIcon(new ImageIcon("./images/i16x16/tex.png"));
popup.add(menuItemtoLatex);
JMenu rmContainer = new JMenu("remove");
rmContainer.setIcon(new ImageIcon("./images/i16x16/delete16.gif"));
popup.add(rmContainer);
menuItemRemove = new JMenuItem("remove completly");
menuItemRemove.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
removeActionPerformed(evt);
}
});
rmContainer.add(menuItemRemove);
rmContainer.addSeparator();
menuItemDeattach = new JMenuItem("deattach from Report");
menuItemDeattach.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
deattachActionPerformed(evt);
}
});
rmContainer.add(menuItemDeattach);
menuItemRemovefromR = new JMenuItem("remove evaluation");
menuItemRemovefromR.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
removefromRActionPerformed(evt);
}
});
rmContainer.add(menuItemRemovefromR);
menuItemRemovefromLatex = new JMenuItem("remove Sweave tag");
menuItemRemovefromLatex.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent evt) {
removefromLatexActionPerformed(evt);
}
});
rmContainer.add(menuItemRemovefromLatex);
// Add listener to the text area so the popup menu can come up.
MouseListener popupListener = new PopupListener(popup);
tree.addMouseListener(popupListener);
}
protected void removefromRActionPerformed(ActionEvent evt) {
if (tree.getSelectionCount() == 0) {
return;
}
if ((tree.getSelectionCount() > 1)
&& !Helper.yesno(
"Remove " + tree.getSelectionCount() + " evaluations?")) {
return;
}
for (TreePath tp : tree.getSelectionPaths()) {
if (tp.getPathCount() == 3) {
String groupname = tp.getPath()[1].toString();
String varname = tp.getPath()[2].toString();
if ((tree.getSelectionCount() == 1)) {
if (!Helper.yesno(
"Remove the evaluation for " + varname + "?")) {
return;
}
}
if (groupname.equals(Constants.STRING_DATA_FILES)) {
MainFrame.jPanelData.rmTable(varname);
Controller.getRTableObjectfromVarname(varname, Controller.getDataFiles(), true).getAttachedRObject().removeFromR();
}
if (groupname.equals(Constants.STRING_TABLES)) {
MainFrame.jPanelTables.rmTable(varname);
Controller.getRTableObjectfromVarname(varname, Controller.getTables(), true).getAttachedRObject().removeFromR();
}
// if ( groupname.equals(Constants.STRING_PLOTS) ) ISOPData.evalAttached(varname);
}
}
this.refresh();
}
protected void removefromLatexActionPerformed(ActionEvent evt) {
if ((tree.getSelectionCount() > 1)
&& !Helper.yesno(
"Remove " + tree.getSelectionCount() + " Sweave tags?")) {
return;
}
for (TreePath tp : tree.getSelectionPaths()) {
if (tp.getPathCount() == 3) {
String groupname = tp.getPath()[1].toString();
IViewport varname = (IViewport)((DefaultMutableTreeNode)tp.getPath()[2]).getUserObject();
if ((tree.getSelectionCount() == 1)) {
if (!Helper.yesno(
"Remove the Sweave-tag for " + varname + "?")) {
return;
}
}
if (groupname.equals(Constants.STRING_DATA_FILES)) {
Controller.rmDatafilefromLatex(varname.getSweaveTag());
}
if (groupname.equals(Constants.STRING_TABLES)) {
Controller.rmTagfromLatex(varname.getSweaveTag());
}
if (groupname.equals(Constants.STRING_PLOTS)) {
Controller.rmTagfromLatex(varname.getSweaveTag());
}
varname.setSweaveTag(null);
}
}
this.refresh();
}
protected void evalActionPerformed(ActionEvent evt) {
if ((tree.getSelectionCount() > 1)
&& !Helper.yesno(
"Evaluate " + tree.getSelectionCount() + " objects?")) {
return;
}
for (TreePath tp : tree.getSelectionPaths()) {
if (tp.getPathCount() == 3) {
String groupname = tp.getPath()[1].toString();
String varname = tp.getPath()[2].toString();
if ((tree.getSelectionCount() == 1)) {
if (!Helper.yesno("Eval " + varname + "?")) {
return;
}
}
if (groupname.equals(Constants.STRING_DATA_FILES)) {
Controller.evalDatafile(varname);
}
if (groupname.equals(Constants.STRING_TABLES)) {
Controller.evalTable(varname);
}
if (groupname.equals(Constants.STRING_PLOTS)) {
Controller.evalPlot(varname);
}
}
}
this.refresh();
}
protected void toLatexActionPerformed(ActionEvent evt) {
for (TreePath tp : tree.getSelectionPaths()) {
if (tp.getPathCount() == 3) {
String groupname = tp.getPath()[1].toString();
String varname = tp.getPath()[2].toString();
if (groupname.equals(Constants.STRING_DATA_FILES)) {
Controller.datafileIntoLatex(varname);
}
if (groupname.equals(Constants.STRING_TABLES)) {
Controller.tableIntoLatex(varname);
}
if (groupname.equals(Constants.STRING_PLOTS)) {
Controller.plotIntoLatex(varname);
}
}
}
this.refresh();
}
public void showActionPerformed(ActionEvent e) {
showSelected();
}
public static void showSelected() {
if (tree.getSelectionCount() != 1) {
return;
}
String groupname = tree.getSelectionPaths()[0].getPath()[1].toString();
if (tree.getSelectionPath().getPathCount() == 2) {
if (groupname.equals(Constants.STRING_DATA_FILES)) {
MainFrame.selectDataPanel();
}
if (groupname.equals(Constants.STRING_TABLES)) {
MainFrame.selectTablePanel();
}
if (groupname.equals(Constants.STRING_PLOTS)) {
MainFrame.selectPlotPanel();
}
}
if (tree.getSelectionPath().getPathCount() == 3) {
DefaultMutableTreeNode varname = (DefaultMutableTreeNode) tree.getSelectionPaths()[0].getLastPathComponent();
if (groupname.equals(Constants.STRING_DATA_FILES)) {
Controller.showDataFile(
((RObjectViewportTable) varname.getUserObject()), true);
}
if (groupname.equals(Constants.STRING_TABLES)) {
Controller.showTable(
(RObjectViewportTable) varname.getUserObject(), true);
}
if (groupname.equals(Constants.STRING_PLOTS)) {
Controller.showPlot((IViewportPlot) varname.getUserObject(),
true);
}
}
refresh();
}
public void gotoSwtActionPerformed(ActionEvent e) {
gotoTag();
}
public static void gotoTag() {
if (tree.getSelectionCount() != 1) {
return;
}
//String groupname = tree.getSelectionPaths()[0].getPath()[1].toString();
MainFrame.selectLatexPanel();
if (tree.getSelectionPath().getPathCount() == 3) {
DefaultMutableTreeNode varname = (DefaultMutableTreeNode) tree.getSelectionPaths()[0].getLastPathComponent();
JLatexPanel.gotoTag(((IViewport) varname.getUserObject()).getSweaveTag());
}
refresh();
}
public void deattachActionPerformed(ActionEvent e) {
for (TreePath sp : tree.getSelectionPaths())
JLatexPanel.deAttachTag(((IViewport)((DefaultMutableTreeNode)sp.getLastPathComponent()).getUserObject()).getSweaveTag());
}
public void removeActionPerformed(ActionEvent e) {
if (tree.getSelectionCount() == 0) {
return;
}
// if only one obj is selected, ask later
if ((tree.getSelectionCount() > 1)
&& !Helper.yesno(
"Remove " + tree.getSelectionCount() + " objects?")) {
return;
}
for (TreePath tp : tree.getSelectionPaths()) {
if (tp.getPathCount() == 2) {
Helper.ok("todo: remove all");
}
if (tp.getPathCount() == 3) {
String groupname = tp.getPath()[1].toString();
Object varname = ((DefaultMutableTreeNode) tp.getLastPathComponent()).getUserObject();
if ((tree.getSelectionCount() == 1)) {
if (!Helper.yesno(
"Remove " + varname + " from " + groupname + "?")) {
return;
}
}
if (((IViewport)varname).isInReport())
JLatexPanel.rmTag(((IViewport)varname).getSweaveTag());
if (groupname.equals(Constants.STRING_DATA_FILES)) {
Controller.removeDataFile((RObjectViewportTable) varname);
}
if (groupname.equals(Constants.STRING_TABLES)) {
Controller.removeTable((RObjectViewportTable) varname);
}
if (groupname.equals(Constants.STRING_PLOTS)) {
Controller.removePlot((IViewportPlot) varname);
}
}
}
}
class PopupListener extends MouseAdapter {
JPopupMenu popup;
PopupListener(JPopupMenu popupMenu) {
popup = popupMenu;
}
public void mousePressed(MouseEvent e) {
maybeShowPopup(e);
}
public void mouseReleased(MouseEvent e) {
maybeShowPopup(e);
}
private void maybeShowPopup(MouseEvent e) {
if (tree.getSelectionCount() == 0) return;
if ((e.getClickCount() == 2)
&& (e.getButton() == MouseEvent.BUTTON1)) {
JRObjectTreePane.showSelected();
}
if (e.isPopupTrigger()) {
boolean allInReport = true;
boolean allEvaled = true;
for (TreePath tp : tree.getSelectionPaths()) {
allInReport &= ((IViewport) ((DefaultMutableTreeNode)tp.getLastPathComponent()).getUserObject()).isInReport();
allEvaled &= ((IViewport) ((DefaultMutableTreeNode)tp.getLastPathComponent()).getUserObject()).getAttachedRObject().isEvaled();
}
System.out.println("allEvaled: " + allEvaled + " allInReport: " + allInReport);
menuItemShow.setVisible(true);
menuItemGotoSwt.setVisible(allInReport && (tree.getSelectionCount() == 1));
menuItemRemove.setVisible(true);
menuItemEval.setVisible(true);
menuItemRemovefromR.setVisible(allEvaled);
menuItemtoLatex.setVisible(!allInReport);
menuItemRemovefromLatex.setVisible(allInReport);
popup.show(e.getComponent(), e.getX(), e.getY());
}
}
private boolean checkInReport(List<IViewport> vp) {
return false;
}
}
}
// TreeDragSource.java
// A drag source wrapper for a JTree. This class can be used to make
// a rearrangeable DnD tree with the TransferableTreeNode class as the
// transfer data type.
class TreeDragSource implements DragSourceListener, DragGestureListener {
DragSource source;
DragGestureRecognizer recognizer;
TransferableSweaveTag transferable;
DefaultMutableTreeNode oldNode;
JTree sourceTree;
public TreeDragSource(JTree tree, int actions) {
sourceTree = tree;
source = new DragSource();
recognizer = source.createDefaultDragGestureRecognizer(sourceTree,
actions, this);
}
/*
* Drag Gesture Handler
*/
public void dragGestureRecognized(DragGestureEvent dge) {
TreePath path = sourceTree.getSelectionPath();
if ((path == null) || (path.getPathCount() <= 2)) {
// We can't move the root node or an empty selection
// TODO: implement moving of whole plots/tebles/... set pathcount to <=1
return;
}
oldNode = (DefaultMutableTreeNode) path.getLastPathComponent();
ISweaveTag swt = ((IViewport) oldNode.getUserObject()).getSweaveTag();
transferable = new TransferableSweaveTag(swt);
source.startDrag(dge, DragSource.DefaultMoveNoDrop, transferable, this);
// If you support dropping the node anywhere, you should probably
// start with a valid move cursor:
// source.startDrag(dge, DragSource.DefaultMoveDrop, transferable,
// this);
}
/*
* Drag Event Handlers
*/
public void dragEnter(DragSourceDragEvent dsde) {}
public void dragExit(DragSourceEvent dse) {}
public void dragOver(DragSourceDragEvent dsde) {}
public void dropActionChanged(DragSourceDragEvent dsde) {
System.out.println("Action: " + dsde.getDropAction());
System.out.println("Target Action: " + dsde.getTargetActions());
System.out.println("User Action: " + dsde.getUserAction());
}
public void dragDropEnd(DragSourceDropEvent dsde) {
/*
* to support move or copy, we have to check which occurred:
*/
System.out.println("Drop Action: " + dsde.getDropAction());
if (dsde.getDropSuccess()) {
System.out.println("success");
}
/*
* to support move only... if (dsde.getDropSuccess()) {
* ((DefaultTreeModel)sourceTree.getModel()).removeNodeFromParent(oldNode); }
*/
}
}