import javax.swing.ImageIcon;
import javax.swing.JLabel;
-
import org.scilab.modules.commons.gui.FindIconHelper;
import org.scilab.modules.localization.Messages;
import org.scilab.modules.types.ScilabTypeEnum;
import org.scilab.modules.types.ScilabTypeEnumDescription;
import org.scilab.modules.ui_data.variablebrowser.ScilabVariableBrowser;
-/**
- *
- * Static class to open/close Scilab Variable browser
- *
- */
+/** Static class to open/close Scilab Variable browser */
public class BrowseVar {
public static final int ICON_COLUMN_INDEX = 0;
public static final int NB_ROWS_INDEX = 8;
public static final int NB_COLS_INDEX = 9;
- public static final String[] COLUMNNAMES = new String[] {"", /* Icon */
- Messages.gettext("Name"),
- Messages.gettext("Value"),
- Messages.gettext("Type"),
- Messages.gettext("Visibility"),
- Messages.gettext("Memory"),
- Messages.gettext("User"),
- Messages.gettext("Type int value"),
- "", /* nbrows */
- "" /* nbcols */
- };
-
- public static final int[] COLUMNSALIGNMENT = new int[] { -1, JLabel.LEFT, JLabel.RIGHT, JLabel.RIGHT, JLabel.RIGHT, JLabel.RIGHT, JLabel.RIGHT, JLabel.RIGHT};
+ public static final String[] COLUMNNAMES =
+ new String[] {
+ "", /* Icon */
+ Messages.gettext("Name"),
+ Messages.gettext("Value"),
+ Messages.gettext("Type"),
+ Messages.gettext("Visibility"),
+ Messages.gettext("Memory"),
+ Messages.gettext("User"),
+ Messages.gettext("Type int value"),
+ "", /* nbrows */
+ "" /* nbcols */
+ };
+
+ public static final int[] COLUMNSALIGNMENT =
+ new int[] {
+ -1,
+ JLabel.LEFT,
+ JLabel.RIGHT,
+ JLabel.RIGHT,
+ JLabel.RIGHT,
+ JLabel.RIGHT,
+ JLabel.RIGHT,
+ JLabel.RIGHT
+ };
private static final ImageIcon NO_ICON = new ImageIcon(FindIconHelper.findIcon("noicon"));
private static final ImageIcon DOUBLE_ICON = new ImageIcon(FindIconHelper.findIcon("double"));
- private static final ImageIcon POLYNOMIAL_ICON = new ImageIcon(FindIconHelper.findIcon("polynomial"));
+ private static final ImageIcon POLYNOMIAL_ICON =
+ new ImageIcon(FindIconHelper.findIcon("polynomial"));
private static final ImageIcon BOOLEAN_ICON = new ImageIcon(FindIconHelper.findIcon("boolean"));
private static final ImageIcon SPARSE_ICON = new ImageIcon(FindIconHelper.findIcon("sparse"));
private static final ImageIcon INT_ICON = new ImageIcon(FindIconHelper.findIcon("int"));
private static final ImageIcon USER_ICON = new ImageIcon(FindIconHelper.findIcon("user"));
private static final ImageIcon FPTR_ICON = new ImageIcon(FindIconHelper.findIcon("fptr"));
- /**
- * Default private constructor for utility class
- */
- private BrowseVar() { }
+ /** Default private constructor for utility class */
+ private BrowseVar() {}
/**
* Get ImageIcon instance from Scilab type (as int)
+ *
* @param type : scilab type as integer
* @return instance of type Icon
*/
case 11:
case 13:
return FUNCTION_ICON;
- /*case 14:
- return LIBRARY_ICON;*/
+ /*case 14:
+ return LIBRARY_ICON;*/
case 15:
return LIST_ICON;
case 16:
}
}
- /**
- * Open Variable Browser
- */
+ /** Open Variable Browser */
public static void openVariableBrowser() {
ScilabVariableBrowser.openVariableBrowser();
}
/**
* Set the Variable Browser data given by Scilab
+ *
* @param dataNames : scilab variable name
* @param dataBytes : scilab variable size in bytes
* @param dataTypes : scilab variable type (as integer)
* @param dataVisibility : local or global variable
* @param dataFromUser : Scilab data or user data
*/
- public static void setVariableBrowserData(String[] dataNames, long[] dataBytes, int[] dataTypes, int[] dataIntegerTypes, String[] variableListTypes, String[] dataSizes, int[] dataNbRows, int[] dataNbCols, String[] dataVisibility, boolean[] dataFromUser) {
+ public static void setVariableBrowserData(
+ String[] dataNames,
+ long[] dataBytes,
+ int[] dataTypes,
+ int[] dataIntegerTypes,
+ String[] variableListTypes,
+ String[] dataSizes,
+ int[] dataNbRows,
+ int[] dataNbCols,
+ String[] dataVisibility,
+ boolean[] dataFromUser) {
Object[][] data = new Object[dataNames.length][COLUMNNAMES.length];
for (int i = 0; i < dataNames.length; ++i) {
data[i][ICON_COLUMN_INDEX] = getIconFromType(dataTypes[i]);
data[i][NAME_COLUMN_INDEX] = dataNames[i];
data[i][SIZE_COLUMN_INDEX] = dataSizes[i];
- data[i][TYPE_DESC_COLUMN_INDEX] = ScilabTypeEnumDescription.getTypeDescriptionFromId(dataTypes[i]);
+ data[i][TYPE_DESC_COLUMN_INDEX] =
+ ScilabTypeEnumDescription.getTypeDescriptionFromId(dataTypes[i]);
if (dataTypes[i] == ScilabTypeEnum.sci_ints.swigValue() && dataIntegerTypes[i] != 0) {
// It is an integer. We want to detail the precision of the int
- data[i][TYPE_DESC_COLUMN_INDEX] = data[i][TYPE_DESC_COLUMN_INDEX] + " " + dataIntegerTypes[i];
+ data[i][TYPE_DESC_COLUMN_INDEX] =
+ data[i][TYPE_DESC_COLUMN_INDEX] + " " + dataIntegerTypes[i];
}
- if ((dataTypes[i] == ScilabTypeEnum.sci_tlist.swigValue() || dataTypes[i] == ScilabTypeEnum.sci_mlist.swigValue()) && !variableListTypes[i].equals("")) {
+ if ((dataTypes[i] == ScilabTypeEnum.sci_tlist.swigValue()
+ || dataTypes[i] == ScilabTypeEnum.sci_mlist.swigValue())
+ && !variableListTypes[i].equals("")) {
// Improve the display of the list
String varType = ScilabTypeEnumDescription.getListTypeDescription(variableListTypes[i]);
}
data[i][VISIBILITY_COLUMN_INDEX] = dataVisibility[i];
data[i][BYTES_COLUMN_INDEX] = humanReadableByteCount(dataBytes[i], true);
- data[i][FROM_SCILAB_COLUMN_INDEX] = dataFromUser[i]; /* Tag if it is a variable from the user or from Scilab (%pi, %eps, etc) */
+ data[i][FROM_SCILAB_COLUMN_INDEX] =
+ dataFromUser[
+ i]; /* Tag if it is a variable from the user or from Scilab (%pi, %eps, etc) */
data[i][TYPE_COLUMN_INDEX] = dataTypes[i];
data[i][NB_ROWS_INDEX] = dataNbRows[i];
data[i][NB_COLS_INDEX] = dataNbCols[i];
}
ScilabVariableBrowser.setVariableBrowserData(data);
}
-
+
/**
* Convert a byte-count into a human readable string
- * @see https://stackoverflow.com/questions/3758606/how-to-convert-byte-size-into-human-readable-format-in-java/3758880#3758880
- *
+ *
+ * @see
+ * https://stackoverflow.com/questions/3758606/how-to-convert-byte-size-into-human-readable-format-in-java/3758880#3758880
* @param bytes the number of bytes
* @param si true if you wish to format as International System, false for Binary System
* @return a formatted string
public static String humanReadableByteCount(long bytes, boolean si) {
int unit = si ? 1000 : 1024;
if (bytes < unit) {
- return bytes + " B";
- }
+ return bytes + " B";
+ }
int exp = (int) (Math.log(bytes) / Math.log(unit));
- String pre = (si ? "kMGTPE" : "KMGTPE").charAt(exp-1) + (si ? "" : "i");
+ String pre = (si ? "kMGTPE" : "KMGTPE").charAt(exp - 1) + (si ? "" : "i");
return String.format("%.1f %sB", bytes / Math.pow(unit, exp), pre);
}
- /**
- * Update Variable Browser
- */
+ /** Update Variable Browser */
public static void updateVariableBrowserData() {
ScilabVariableBrowser.updateVariableBrowser();
}
- /**
- * @return true if an instance of BrowseVar already exists.
- */
+ /** @return true if an instance of BrowseVar already exists. */
public static boolean isVariableBrowserOpened() {
return ScilabVariableBrowser.isBrowseVarOpened();
}
- /**
- * Close Variable Browser
- */
+ /** Close Variable Browser */
public static void closeVariableBrowser() {
ScilabVariableBrowser.closeVariableBrowser();
}
import java.util.Comparator;
import java.util.TreeSet;
import java.util.regex.Pattern;
-
import javax.swing.Icon;
import javax.swing.SortOrder;
-
import org.scilab.modules.commons.CommonFileUtils;
import org.scilab.modules.commons.ScilabConstants;
import org.scilab.modules.ui_data.utils.UiDataMessages;
/**
* Handle a File as a node in the JTree
+ *
* @author Calixte DENIZET
*/
public class FileNode {
/**
* Default constructor
+ *
* @param file the file in this node
*/
public FileNode(File file, int position) {
return position;
}
- /**
- * @param pat the pattern to filter the files
- */
+ /** @param pat the pattern to filter the files */
public void setFilter(Pattern pat) {
this.pat = pat;
resetChildren();
}
/**
- * @param order the order to use to sort the file. If order is positive, then ascending order is used.
+ * @param order the order to use to sort the file. If order is positive, then ascending order is
+ * used.
*/
public void setOrder(int order) {
this.order = order;
setOrder(sign * order);
}
- /**
- * @return the used order
- */
+ /** @return the used order */
public SortOrder getOrder() {
return order > 0 ? SortOrder.ASCENDING : SortOrder.DESCENDING;
}
/**
* Sort a column according to the natural order for its.
+ *
* @param nameColumn the column name
*/
public void toggleSortOrder(String nameColumn) {
/**
* Sort the files
+ *
* @param order the order to use
* @param files the files to order
* @return the ordered FileNodes
}
}
- /**
- * Returns the string to be used to display this leaf in the JTree.
- */
+ /** Returns the string to be used to display this leaf in the JTree. */
public String toString() {
String name = file.getName();
if (name.isEmpty()) {
return name;
}
- /**
- * @return the file associated with this node
- */
+ /** @return the file associated with this node */
public File getFile() {
return file;
}
- /**
- * @return true if this represents the user-home directory
- */
+ /** @return true if this represents the user-home directory */
public boolean isUserHome() {
return userHome;
}
- /**
- * @return true if this represents the SCI directory
- */
+ /** @return true if this represents the SCI directory */
public boolean isSCI() {
return sci;
}
- /**
- * @return the last modified time for this file
- */
+ /** @return the last modified time for this file */
public long getLastModified() {
return lastModified;
}
- /**
- * @return the icon associated with this file
- */
+ /** @return the icon associated with this file */
public Icon getIcon() {
if (icon == null) {
icon = FileUtils.getIconForFile(file);
return icon;
}
- /**
- * @return true if the file is not a directory or if it is an empty one
- */
+ /** @return true if the file is not a directory or if it is an empty one */
public boolean isLeaf() {
return isEmpty;
}
- /**
- * @return the number of files in the directory representated by this file
- */
+ /** @return the number of files in the directory representated by this file */
public int getChildrenCount() {
if (!isEmpty) {
synchronized (file) {
return 0;
}
- /**
- * @return the children FileNode of this FileNode
- */
+ /** @return the children FileNode of this FileNode */
protected Object[] getChildren() {
if (children == null && !isEmpty) {
children = listFiles();
return children;
}
+ public FileNode[] getRawChildren() {
+ return children;
+ }
+
public FileNode[] listFiles() {
String[] filesName = file.list();
if (filesName != null) {
return null;
}
- /**
- * Reset children only
- */
+ /** Reset children only */
public void resetChildren() {
children = null;
+ isEmpty = isFile || CommonFileUtils.isEmptyDirectory(file.getAbsolutePath()) == 1;
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public boolean equals(Object o) {
return (o instanceof FileNode) && ((FileNode) o).file.equals(file);
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public int hashCode() {
return file.hashCode();
}
/*
* Scilab ( http://www.scilab.org/ ) - This file is part of Scilab
* Copyright (C) 2011 - DIGITEO - Calixte DENIZET
+ * Copyright (C) 2020 - ESI Group - Clement DAVID
*
* Copyright (C) 2012 - 2016 - Scilab Enterprises
*
* along with this program.
*
*/
-
package org.scilab.modules.ui_data.filebrowser;
import java.io.File;
+import java.io.IOException;
+import java.nio.file.FileSystems;
+import java.nio.file.Path;
+import java.nio.file.StandardWatchEventKinds;
+import java.nio.file.WatchEvent;
+import java.nio.file.WatchKey;
+import java.nio.file.WatchService;
+import java.nio.file.Watchable;
import java.text.DecimalFormat;
+import java.util.ArrayList;
import java.util.Date;
+import java.util.Iterator;
+import java.util.List;
+import java.util.logging.Level;
+import java.util.logging.Logger;
import java.util.regex.Pattern;
-
+import java.util.stream.Collectors;
import javax.swing.SwingWorker;
-
import org.scilab.modules.ui_data.utils.UiDataMessages;
/**
* The tree table model abstract implementation
+ *
* @author Calixte DENIZET
*/
-public class ScilabFileBrowserModel extends AbstractScilabTreeTableModel implements ScilabTreeTableModel {
+public class ScilabFileBrowserModel extends AbstractScilabTreeTableModel
+ implements ScilabTreeTableModel {
- private static final String[] names = {UiDataMessages.NAME_COLUMN,
- UiDataMessages.SIZE_COLUMN,
- UiDataMessages.TYPE_COLUMN,
- UiDataMessages.LASTMODIF_COLUMN
- };
+ private static final String[] names = {
+ UiDataMessages.NAME_COLUMN, UiDataMessages.SIZE_COLUMN,
+ UiDataMessages.TYPE_COLUMN, UiDataMessages.LASTMODIF_COLUMN
+ };
- private static final Class[] types = {ScilabTreeTableModel.class,
- FileSize.class,
- String.class,
- Date.class
- };
+ private static final Class[] types = {
+ ScilabTreeTableModel.class, FileSize.class, String.class, Date.class
+ };
private static final FileSize MINUSONE = new FileSize(-1);
+ /** Will trigger a model update on file creation/deletion */
+ private final class DirWatcher extends SwingWorker<Void, Object[]> {
+
+ public DirWatcher(FileNode root) {
+ watchDirectories(new Object[] {root});
+ }
+
+ @Override
+ protected Void doInBackground() throws Exception {
+ for (; ; ) {
+ WatchKey key = watcher.take();
+ List<FileNode> treePath = new ArrayList<>();
+ FileNode fn = null;
+
+ // identify the associated file and publish for update on EDT
+ Watchable wa = key.watchable();
+ if (wa instanceof Path) {
+ Path p = (Path) wa;
+ Path r = ((FileNode) root).file.toPath().relativize(p);
+
+ // reconstruct a TreePath
+ treePath.add((FileNode) root);
+ Iterator<Path> it = r.iterator();
+ while (it.hasNext()) {
+ Path name = it.next();
+ FileNode[] children = (FileNode[]) treePath.get(treePath.size() - 1).getChildren();
+ for (FileNode node : children) {
+ if (node.name.equals(name.toString())) {
+ treePath.add(node);
+ break;
+ }
+ }
+ }
+
+ // in case of directory deletion, only reset the hierarchy up to an
+ // existing directory
+ treePath = treePath.stream().filter(n -> n.file.exists()).collect(Collectors.toList());
+ if (treePath.isEmpty()) {
+ // if the root is remove then cancel the watcher
+ watcher.close();
+ watcher = null;
+ return null;
+ }
+
+ // retrieve the corresponding FileNode
+ fn = treePath.get(treePath.size() - 1);
+
+ // reset the children of the FileNode
+ fn.resetChildren();
+ Object[] children = fn.getChildren();
+
+ // on directory creation, add them to the watch list
+ watchDirectories(children);
+ }
+
+ // trigger a refresh on the EDT for the full treepath
+ publish(new Object[] {key, treePath.toArray()});
+ }
+ }
+
+ @Override
+ protected void process(List<Object[]> chunks) {
+ for (Object[] o : chunks) {
+ WatchKey key = (WatchKey) o[0];
+ Object[] path = (Object[]) o[1];
+
+ List<WatchEvent<?>> events = key.pollEvents();
+ if (events.isEmpty()) {
+ continue;
+ }
+
+ // reinstall a watch on the directory
+ key.reset();
+
+ // reload part of the model
+ ScilabFileBrowserModel.this.fireTreeStructureChanged(this, path, null, null);
+ }
+ }
+
+ /**
+ * append directories to be watched
+ *
+ * @param children file list
+ */
+ public void watchDirectories(Object[] children) {
+ for (Object o : children) {
+ if (!(o instanceof FileNode)) {
+ continue;
+ }
+ FileNode fn = (FileNode) o;
+ if (fn.isFile) {
+ continue;
+ }
+ Path p = fn.file.toPath();
+ try {
+ p.register(
+ watcher, StandardWatchEventKinds.ENTRY_CREATE, StandardWatchEventKinds.ENTRY_DELETE);
+ } catch (IOException ex) {
+ ex.printStackTrace();
+ Logger.getLogger(SwingScilabTreeTable.class.getName()).log(Level.SEVERE, null, ex);
+ cancel(false);
+ }
+ }
+ }
+ }
+
private int order = 1;
private String baseDir = "";
+ WatchService watcher;
+ private DirWatcher dirWatcher;
- /**
- * Default constructor
- */
+ /** Default constructor */
public ScilabFileBrowserModel() {
super();
+
+ try {
+ // Setup watchers
+ watcher = FileSystems.getDefault().newWatchService();
+ } catch (IOException ex) {
+ Logger.getLogger(SwingScilabTreeTable.class.getName()).log(Level.SEVERE, null, ex);
+ watcher = null;
+ }
}
/**
* Set the base directory
+ *
* @param baseDir the base directory
* @param stt the associated treetable component
*/
public void setBaseDir(final String baseDir, final SwingScilabTreeTable stt) {
this.baseDir = baseDir;
- SwingWorker worker = new SwingWorker<Void, Void>() {
+ SwingWorker worker =
+ new SwingWorker<Void, Void>() {
protected Void doInBackground() throws Exception {
File f = new File(baseDir);
setRoot(new FileNode(f, -1));
public void setRoot(Object root) {
super.setRoot(root);
- // Force the root to load its children in the SwingWorker thread rather than in EDT
- ((FileNode) root).getChildrenCount();
+ // watch for changes
+ if (watcher != null) {
+ if (dirWatcher != null) {
+ dirWatcher.cancel(true);
+ }
+ dirWatcher = new DirWatcher((FileNode) root);
+ dirWatcher.execute();
+ }
+
+ // Force the root to load its children in the SwingWorker thread rather than in
+ // EDT
+ watchDirectories(((FileNode) root).getChildren());
}
- /**
- * @return the base directory of this model
- */
+ Object[] watchDirectories(Object[] objects) {
+ if (watcher != null && dirWatcher != null && objects != null) {
+ dirWatcher.watchDirectories(objects);
+ }
+ return objects;
+ }
+
+ /** @return the base directory of this model */
public String getBaseDir() {
return baseDir;
}
/**
* Set the filter pattern
+ *
* @pat the pattern
*/
public void setFilter(Pattern pat) {
*/
protected Object[] getChildren(Object node) {
FileNode fileNode = (FileNode) node;
- return fileNode.getChildren();
+ FileNode[] raw = fileNode.getRawChildren();
+ if (raw == null) {
+ return watchDirectories(fileNode.getChildren());
+ } else {
+ return fileNode.getChildren();
+ }
}
/**
* @return the number of children of this node
*/
public int getChildCount(Object node) {
- int count = ((FileNode) node).getChildrenCount();
+ Object[] children = getChildren(node);
+ int count = 0;
+ if (children != null) {
+ count = children.length;
+ }
+
if (parent == null || node != getRoot()) {
return count;
}
return node != getRoot() && ((FileNode) node).isLeaf();
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public int getColumnCount() {
- // TODO : remove the comment and let the choice to the user to remove or not the columns
- return 1;//names.length;
+ // TODO : remove the comment and let the choice to the user to remove or not the
+ // columns
+ return 1; // names.length;
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public String getColumnName(int column) {
return names[column];
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public Class getColumnClass(int column) {
return types[column];
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public Object getValueAt(Object node, int column) {
File file = getFile(node);
try {
case 3:
return new Date(file.lastModified());
}
- } catch (SecurityException se) { }
+ } catch (SecurityException se) {
+ }
return null;
}
- /**
- * Inner class to represent the parent node of a file node
- */
+ /** Inner class to represent the parent node of a file node */
public static class ParentNode extends FileNode {
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public ParentNode(File f) {
super(f, -1);
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public boolean isLeaf() {
return true;
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public String toString() {
return "..";
}
}
- /**
- * Inner class to represent the size of file
- */
+ /** Inner class to represent the size of file */
public static class FileSize {
int size;
package org.scilab.modules.ui_data.filebrowser;
-import javax.swing.table.AbstractTableModel;
import javax.swing.JTree;
-import javax.swing.tree.TreePath;
import javax.swing.event.TreeExpansionEvent;
import javax.swing.event.TreeExpansionListener;
+import javax.swing.event.TreeModelEvent;
+import javax.swing.event.TreeModelListener;
+import javax.swing.table.AbstractTableModel;
+import javax.swing.tree.TreePath;
/**
* The tree table model abstract implementation
+ *
* @author Calixte DENIZET
*/
-@SuppressWarnings(value = { "serial" })
+@SuppressWarnings(value = {"serial"})
public class ScilabTreeTableModelAdapter extends AbstractTableModel {
private JTree tree;
/**
* Default constructor
+ *
* @param treeTableModel the table model
* @param tree the tree
*/
public ScilabTreeTableModelAdapter(ScilabTreeTableModel treeTableModel, JTree tree) {
this.tree = tree;
this.treeTableModel = treeTableModel;
- tree.addTreeExpansionListener(new TreeExpansionListener() {
+ tree.addTreeExpansionListener(
+ new TreeExpansionListener() {
public void treeExpanded(TreeExpansionEvent event) {
fireTableDataChanged();
}
+
public void treeCollapsed(TreeExpansionEvent event) {
fireTableDataChanged();
}
});
+ tree.getModel()
+ .addTreeModelListener(
+ new TreeModelListener() {
+
+ @Override
+ public void treeStructureChanged(TreeModelEvent e) {
+ fireTableDataChanged();
+ }
+
+ @Override
+ public void treeNodesRemoved(TreeModelEvent e) {
+ fireTableDataChanged();
+ }
+
+ @Override
+ public void treeNodesInserted(TreeModelEvent e) {
+ fireTableDataChanged();
+ }
+
+ @Override
+ public void treeNodesChanged(TreeModelEvent e) {
+ fireTableDataChanged();
+ }
+ });
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public int getColumnCount() {
return treeTableModel.getColumnCount();
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public String getColumnName(int column) {
return treeTableModel.getColumnName(column);
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public Class getColumnClass(int column) {
return treeTableModel.getColumnClass(column);
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public int getRowCount() {
return tree.getRowCount();
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
protected Object nodeForRow(int row) {
TreePath treePath = tree.getPathForRow(row);
return treePath.getLastPathComponent();
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public Object getValueAt(int row, int column) {
return treeTableModel.getValueAt(nodeForRow(row), column);
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public boolean isCellEditable(int row, int column) {
return treeTableModel.isCellEditable(nodeForRow(row), column);
}
- /**
- * {@inheritdoc}
- */
+ /** {@inheritdoc} */
public void setValueAt(Object value, int row, int column) {
treeTableModel.setValueAt(value, nodeForRow(row), column);
}
import java.text.DateFormat;
import java.util.Date;
import java.util.regex.Pattern;
-
import javax.swing.ActionMap;
import javax.swing.ImageIcon;
import javax.swing.InputMap;
import javax.swing.JTable;
import javax.swing.KeyStroke;
import javax.swing.SwingUtilities;
+import javax.swing.SwingWorker;
import javax.swing.border.AbstractBorder;
import javax.swing.border.Border;
import javax.swing.plaf.basic.BasicTreeUI;
import javax.swing.table.DefaultTableCellRenderer;
-import javax.swing.SwingWorker;
import javax.swing.tree.TreePath;
-
import org.scilab.modules.commons.gui.FindIconHelper;
import org.scilab.modules.gui.events.callback.CommonCallBack;
import org.scilab.modules.ui_data.filebrowser.actions.ChangeCWDAction;
/**
* The tree table model abstract implementation
+ *
* @author Calixte DENIZET
*/
-@SuppressWarnings(value = { "serial" })
+@SuppressWarnings(value = {"serial"})
public class SwingScilabTreeTable extends JTable {
private static final Insets INSETS = new Insets(0, 2, 0, 0);
- private static final DateFormat DATEFORMAT = DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.MEDIUM);
+ private static final DateFormat DATEFORMAT =
+ DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.MEDIUM);
- private static final Border BORDER = new AbstractBorder() {
+ private static final Border BORDER =
+ new AbstractBorder() {
public void paintBorder(Component c, Graphics g, int x, int y, int width, int height) {
g.setColor(Color.LIGHT_GRAY);
g.drawLine(x, y, x, y + height);
private SwingWorker dirRefresher;
private ScilabFileBrowserModel model;
- private boolean resetScrollBar = true;
private Method isLocationInExpandControl;
protected ScilabTreeTableCellRenderer tree;
protected ScilabFileSelectorComboBox combobox;
protected ScilabFileBrowserHistory history;
-
+
/**
* Default Constructor
+ *
* @param treeTableModel the tree table model
* @param combobox the combox used to set the path
*/
- public SwingScilabTreeTable(ScilabTreeTableModel treeTableModel, ScilabFileSelectorComboBox combobox) {
+ public SwingScilabTreeTable(
+ ScilabTreeTableModel treeTableModel, ScilabFileSelectorComboBox combobox) {
super();
this.combobox = combobox;
combobox.setTreeTable(this);
// Install the tree editor renderer and editor.
setDefaultRenderer(ScilabTreeTableModel.class, tree);
- setDefaultRenderer(Date.class, new DefaultTableCellRenderer() {
+ setDefaultRenderer(
+ Date.class,
+ new DefaultTableCellRenderer() {
{
setHorizontalTextPosition(DefaultTableCellRenderer.LEFT);
}
- public Component getTableCellRendererComponent(JTable table, Object value, boolean selected, boolean focus, int row, int col) {
- JLabel label = (JLabel) super.getTableCellRendererComponent(table, value, selected, focus, row, col);
+ public Component getTableCellRendererComponent(
+ JTable table, Object value, boolean selected, boolean focus, int row, int col) {
+ JLabel label =
+ (JLabel)
+ super.getTableCellRendererComponent(table, value, selected, focus, row, col);
label.setText(DATEFORMAT.format((Date) value));
if (col == 1) {
label.setBorder(BORDER);
return label;
}
});
- setDefaultRenderer(ScilabFileBrowserModel.FileSize.class, new DefaultTableCellRenderer() {
+ setDefaultRenderer(
+ ScilabFileBrowserModel.FileSize.class,
+ new DefaultTableCellRenderer() {
{
setHorizontalTextPosition(DefaultTableCellRenderer.LEFT);
}
- public Component getTableCellRendererComponent(JTable table, Object value, boolean selected, boolean focus, int row, int col) {
- Component c = super.getTableCellRendererComponent(table, value, selected, focus, row, col);
+ public Component getTableCellRendererComponent(
+ JTable table, Object value, boolean selected, boolean focus, int row, int col) {
+ Component c =
+ super.getTableCellRendererComponent(table, value, selected, focus, row, col);
if (col == 1) {
JLabel jl = (JLabel) c;
jl.setBorder(BORDER);
return c;
}
});
- setDefaultRenderer(String.class, new DefaultTableCellRenderer() {
+ setDefaultRenderer(
+ String.class,
+ new DefaultTableCellRenderer() {
{
setHorizontalTextPosition(DefaultTableCellRenderer.LEFT);
}
- public Component getTableCellRendererComponent(JTable table, Object value, boolean selected, boolean focus, int row, int col) {
- Component c = super.getTableCellRendererComponent(table, value, selected, focus, row, col);
+ public Component getTableCellRendererComponent(
+ JTable table, Object value, boolean selected, boolean focus, int row, int col) {
+ Component c =
+ super.getTableCellRendererComponent(table, value, selected, focus, row, col);
if (col == 1) {
JLabel jl = (JLabel) c;
jl.setBorder(BORDER);
setAutoResizeMode(AUTO_RESIZE_NEXT_COLUMN);
try {
- isLocationInExpandControl = BasicTreeUI.class.getDeclaredMethod("isLocationInExpandControl", new Class[] {TreePath.class, int.class, int.class});
+ isLocationInExpandControl =
+ BasicTreeUI.class.getDeclaredMethod(
+ "isLocationInExpandControl", new Class[] {TreePath.class, int.class, int.class});
isLocationInExpandControl.setAccessible(true);
- } catch (NoSuchMethodException e) { }
+ } catch (NoSuchMethodException e) {
+ }
- addMouseListener(new MouseAdapter() {
+ addMouseListener(
+ new MouseAdapter() {
public void mousePressed(MouseEvent e) {
Point p = e.getPoint();
int col = columnAtPoint(p);
- if (getColumnClass(col) == ScilabTreeTableModel.class && SwingUtilities.isLeftMouseButton(e)) {
+ if (getColumnClass(col) == ScilabTreeTableModel.class
+ && SwingUtilities.isLeftMouseButton(e)) {
MouseEvent me = e;
if (isLocationInExpandControl != null) {
try {
int row = rowAtPoint(p);
TreePath path = tree.getPathForRow(row);
- boolean isOnExpander = ((Boolean) isLocationInExpandControl.invoke(tree.getUI(), path, e.getX(), e.getY())).booleanValue();
+ boolean isOnExpander =
+ ((Boolean)
+ isLocationInExpandControl.invoke(
+ tree.getUI(), path, e.getX(), e.getY()))
+ .booleanValue();
Rectangle r = tree.getRowBounds(row);
if (!isOnExpander && !r.contains(p)) {
- me = new MouseEvent((Component) e.getSource(), e.getID(), e.getWhen(), e.getModifiers(), r.x, r.y, e.getClickCount(), e.isPopupTrigger());
+ me =
+ new MouseEvent(
+ (Component) e.getSource(),
+ e.getID(),
+ e.getWhen(),
+ e.getModifiers(),
+ r.x,
+ r.y,
+ e.getClickCount(),
+ e.isPopupTrigger());
}
- } catch (Exception ex) { }
+ } catch (Exception ex) {
+ }
}
tree.dispatchEvent(me);
}
}
});
- addKeyListener(new KeyAdapter() {
+ addKeyListener(
+ new KeyAdapter() {
public void keyTyped(KeyEvent e) {
char c = e.getKeyChar();
if (Character.isLetter(c)) {
start = modulo(rows[0] + step, count);
}
for (int i = start; i != start - step; i = modulo(i + step, count)) {
- char first = ((FileNode) tree.getPathForRow(i).getLastPathComponent()).toString().charAt(0);
+ char first =
+ ((FileNode) tree.getPathForRow(i).getLastPathComponent()).toString().charAt(0);
first = Character.toLowerCase(first);
if (first == c) {
scrollRectToVisible(tree.getRowBounds(i));
}
});
-
initActions();
setComponentPopupMenu(createPopup());
}
- /**
- * @return the Next button used in history
- */
+ /** @return the Next button used in history */
public JButton getNextButton() {
return history.getNextButton();
}
- /**
- * @return the Previous button used in history
- */
+ /** @return the Previous button used in history */
public JButton getPreviousButton() {
return history.getPreviousButton();
}
- /**
- * @return the combobox used to set the path
- */
+ /** @return the combobox used to set the path */
public ScilabFileSelectorComboBox getComboBox() {
return combobox;
}
/**
* Get the selected rows as file path
+ *
* @return the paths
*/
public String[] getSelectedPaths() {
/**
* Get the selected rows as file
+ *
* @return the paths
*/
public File[] getSelectedFiles() {
return files;
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public int getRowHeight(int row) {
return getRowHeight();
}
- /**
- * {@inheritDoc}
- */
+ /** {@inheritDoc} */
public boolean isOpaque() {
return false;
}
/**
* Set the base directory
+ *
* @param baseDir the base directory
*/
public void setBaseDir(String baseDir) {
/**
* Set the base directory
+ *
* @param baseDir the base directory
* @param addInHistory if true the dir is add in the history
*/
}
combobox.setBaseDir(baseDir);
if (model != null) {
+ boolean sameDir = baseDir.equals(model.getBaseDir());
File f = new File(baseDir);
- if (cancelled || (f.exists() && f.isDirectory() && f.canRead())) {
- boolean sameDir = baseDir.equals(model.getBaseDir());
+ if (cancelled || (!sameDir && f.exists() && f.isDirectory() && f.canRead())) {
tree.setModel(null);
- if (!sameDir && addInHistory) {
+ if (addInHistory) {
history.addPathInHistory(baseDir);
}
- resetScrollBar = !sameDir;
model.setBaseDir(baseDir, this);
}
}
/**
* Set the file filter to use in table
+ *
* @param pat the pattern to use
*/
public void setFilter(Pattern pat) {
reload(model);
}
- /**
- * Reload the table
- */
+ /** Reload the table */
public void reload(ScilabFileBrowserModel model) {
tree.setModel(model);
tree.setRowHeight(getRowHeight());
tree.setLargeModel(true);
TreePath path = new TreePath(model.getRoot());
tree.collapsePath(path);
- if (resetScrollBar) {
- ((JScrollPane) SwingUtilities.getAncestorOfClass(JScrollPane.class, this)).getVerticalScrollBar().setValue(0);
- }
- resetScrollBar = true;
+ ((JScrollPane) SwingUtilities.getAncestorOfClass(JScrollPane.class, this))
+ .getVerticalScrollBar()
+ .setValue(0);
tree.expandPath(path);
if (getRowCount() >= 1) {
repaint(tree.getRowBounds(0));
editingRow = 0;
}
- /* Workaround for BasicTableUI anomaly. Make sure the UI never tries to
- * paint the editor. The UI currently uses different techniques to
- * paint the renderers and editors and overriding setBounds() below
- * is not the right thing to do for an editor. Returning -1 for the
- * editing row in this case, ensures the editor is never painted.
+ /*
+ * Workaround for BasicTableUI anomaly. Make sure the UI never tries to paint
+ * the editor. The UI currently uses different techniques to paint the renderers
+ * and editors and overriding setBounds() below is not the right thing to do for
+ * an editor. Returning -1 for the editing row in this case, ensures the editor
+ * is never painted.
*/
public int getEditingRow() {
if (getColumnClass(editingColumn) == ScilabTreeTableModel.class) {
}
}
- /**
- * Init the actions
- */
+ /** Init the actions */
private void initActions() {
final ActionMap actions = getActionMap();
actions.put("scinotes", new OpenFileInSciNotesAction(this));
actions.put("open", new OpenFileWithDefaultAppAction(this));
}
actions.put("validate", new ValidateAction(this));
- actions.put("validateorexpand", new CommonCallBack(null) {
+ actions.put(
+ "validateorexpand",
+ new CommonCallBack(null) {
public void callBack() {
int[] rows = getSelectedRows();
if (rows != null && rows.length != 0) {
map.put(KeyStroke.getKeyStroke("ENTER"), "validateorexpand");
}
- /**
- * Create the popup menu
- */
+ /** Create the popup menu */
private JPopupMenu createPopup() {
ActionMap actions = getActionMap();
JPopupMenu popup = new JPopupMenu();
return popup;
}
-
public synchronized void setDirRefresher(SwingWorker refresher, ScilabFileBrowserModel model) {
dirRefresher = refresher;
this.model = model;
/**
* A modulo for negative numbers
+ *
* @param n an int
* @param p another int
* @return n modulo p
}
return p - (-n % p);
}
-
}