19 package org.sleuthkit.autopsy.corecomponents;
21 import com.google.common.eventbus.Subscribe;
22 import java.awt.Component;
23 import java.awt.Cursor;
24 import java.awt.FontMetrics;
25 import java.awt.Graphics;
26 import java.awt.dnd.DnDConstants;
27 import java.awt.event.MouseAdapter;
28 import java.awt.event.MouseEvent;
29 import java.beans.FeatureDescriptor;
30 import java.beans.PropertyChangeEvent;
31 import java.beans.PropertyVetoException;
32 import java.lang.reflect.InvocationTargetException;
33 import java.util.ArrayList;
34 import java.util.Comparator;
35 import java.util.HashMap;
36 import java.util.LinkedList;
37 import java.util.List;
39 import java.util.Queue;
40 import java.util.TreeMap;
41 import java.util.TreeSet;
42 import java.util.concurrent.ConcurrentHashMap;
43 import java.util.logging.Level;
44 import java.util.prefs.PreferenceChangeEvent;
45 import java.util.prefs.Preferences;
46 import javax.swing.ImageIcon;
47 import javax.swing.JOptionPane;
48 import javax.swing.JTable;
49 import javax.swing.ListSelectionModel;
50 import static javax.swing.SwingConstants.CENTER;
51 import javax.swing.SwingUtilities;
52 import javax.swing.event.ChangeEvent;
53 import javax.swing.event.ListSelectionEvent;
54 import javax.swing.event.TableColumnModelEvent;
55 import javax.swing.event.TableColumnModelListener;
56 import javax.swing.event.TreeExpansionListener;
57 import javax.swing.table.TableCellRenderer;
58 import javax.swing.table.TableColumn;
59 import javax.swing.table.TableColumnModel;
60 import org.netbeans.swing.etable.ETableColumn;
61 import org.netbeans.swing.etable.ETableColumnModel;
62 import org.netbeans.swing.outline.DefaultOutlineCellRenderer;
63 import org.netbeans.swing.outline.DefaultOutlineModel;
64 import org.netbeans.swing.outline.Outline;
65 import org.openide.explorer.ExplorerManager;
66 import org.openide.explorer.view.OutlineView;
67 import org.openide.nodes.AbstractNode;
68 import org.openide.nodes.Children;
69 import org.openide.nodes.Node;
70 import org.openide.nodes.Node.Property;
71 import org.openide.nodes.NodeEvent;
72 import org.openide.nodes.NodeListener;
73 import org.openide.nodes.NodeMemberEvent;
74 import org.openide.nodes.NodeReorderEvent;
75 import org.openide.util.ImageUtilities;
76 import org.openide.util.NbBundle;
77 import org.openide.util.NbPreferences;
78 import org.openide.util.lookup.ServiceProvider;
101 @ServiceProvider(service = DataResultViewer.class)
102 @SuppressWarnings(
"PMD.SingularField")
105 private static final long serialVersionUID = 1L;
108 private static final String NOTEPAD_ICON_PATH =
"org/sleuthkit/autopsy/images/notepad16.png";
109 private static final String RED_CIRCLE_ICON_PATH =
"org/sleuthkit/autopsy/images/red-circle-exclamation.png";
110 private static final String YELLOW_CIRCLE_ICON_PATH =
"org/sleuthkit/autopsy/images/yellow-circle-yield.png";
111 private static final ImageIcon COMMENT_ICON =
new ImageIcon(ImageUtilities.loadImage(NOTEPAD_ICON_PATH,
false));
112 private static final ImageIcon INTERESTING_SCORE_ICON =
new ImageIcon(ImageUtilities.loadImage(YELLOW_CIRCLE_ICON_PATH,
false));
113 private static final ImageIcon NOTABLE_ICON_SCORE =
new ImageIcon(ImageUtilities.loadImage(RED_CIRCLE_ICON_PATH,
false));
114 @NbBundle.Messages(
"DataResultViewerTable.firstColLbl=Name")
115 static private final String FIRST_COLUMN_LABEL = Bundle.DataResultViewerTable_firstColLbl();
129 private final Map<String, PagingSupport> nodeNameToPagingSupportMap =
new ConcurrentHashMap<>();
144 this(null, Bundle.DataResultViewerTable_title());
157 this(explorerManager, Bundle.DataResultViewerTable_title());
171 super(explorerManager);
173 this.columnMap =
new HashMap<>();
174 this.propertiesMap =
new TreeMap<>();
181 initializePagingSupport();
187 exportCSVButton.setEnabled(
false);
193 outlineView.setAllowedDragActions(DnDConstants.ACTION_NONE);
195 outline = outlineView.getOutline();
196 outline.setRowSelectionAllowed(
true);
197 outline.setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);
198 outline.setRootVisible(
false);
199 outline.setDragEnabled(
false);
206 outline.getColumnModel().addColumnModelListener(outlineViewListener);
209 outline.getColumnModel().addColumnModelListener(iconRendererListener);
215 outline.getTableHeader().addMouseListener(outlineViewListener);
219 if (pagingSupport == null) {
232 setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
237 nodeNameToPagingSupportMap.values().forEach((ps) -> {
238 ps.postPageSizeChangeEvent();
264 @NbBundle.Messages(
"DataResultViewerTable.title=Table")
289 public
void setNode(Node rootNode) {
290 if (!SwingUtilities.isEventDispatchThread()) {
291 LOGGER.log(Level.SEVERE,
"Attempting to run setNode() from non-EDT thread");
302 outline.unsetQuickFilter();
304 this.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
306 if (rootNode != null) {
307 this.rootNode = rootNode;
313 String nodeName = rootNode.getName();
314 pagingSupport = nodeNameToPagingSupportMap.get(nodeName);
315 if (pagingSupport == null) {
317 nodeNameToPagingSupportMap.put(nodeName, pagingSupport);
321 rootNode.addNodeListener(
new NodeListener() {
323 public void childrenAdded(NodeMemberEvent nme) {
330 SwingUtilities.invokeLater(() -> {
336 public void childrenRemoved(NodeMemberEvent nme) {
337 SwingUtilities.invokeLater(() -> {
343 public void childrenReordered(NodeReorderEvent nre) {
348 public void nodeDestroyed(NodeEvent ne) {
353 public void propertyChange(PropertyChangeEvent evt) {
370 if (rootNode != null && rootNode.getChildren().getNodesCount() > 0) {
371 this.getExplorerManager().setRootContext(this.rootNode);
374 Node emptyNode =
new AbstractNode(Children.LEAF);
375 this.getExplorerManager().setRootContext(emptyNode);
376 outline.setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
378 outlineView.setPropertyColumns();
381 this.setCursor(null);
392 outlineView.addTreeExpansionListener(listener);
417 List<Node.Property<?>> props = loadColumnOrder();
418 boolean propsExist = props.isEmpty() ==
false;
419 Node.Property<?> firstProp = null;
421 firstProp = props.remove(0);
429 outline.setAutoResizeMode((props.isEmpty()) ? JTable.AUTO_RESIZE_ALL_COLUMNS : JTable.AUTO_RESIZE_OFF);
431 assignColumns(props);
432 if (firstProp != null) {
433 ((DefaultOutlineModel) outline.getOutlineModel()).setNodesColumnLabel(firstProp.getDisplayName());
457 loadColumnVisibility();
464 NodeSelectionInfo selectedChildInfo = ((TableFilterNode) rootNode).getChildNodeSelectionInfo();
465 if (null != selectedChildInfo) {
466 Node[] childNodes = rootNode.getChildren().getNodes(
true);
467 for (
int i = 0; i < childNodes.length; ++i) {
468 Node childNode = childNodes[i];
469 if (selectedChildInfo.
matches(childNode)) {
470 SwingUtilities.invokeLater(() -> {
472 this.getExplorerManager().setExploredContextAndSelection(this.rootNode,
new Node[]{childNode});
473 }
catch (PropertyVetoException ex) {
474 LOGGER.log(Level.SEVERE,
"Failed to select node specified by selected child info", ex);
481 ((TableFilterNode) rootNode).setChildNodeSelectionInfo(null);
500 TableColumnModel columnModel = outline.getColumnModel();
501 int columnCount = columnModel.getColumnCount();
503 for (Map.Entry<Integer, Property<?>> entry : propertiesMap.entrySet()) {
504 final String propName = entry.getValue().getName();
505 if (entry.getKey() < columnCount) {
506 final ETableColumn column = (ETableColumn) columnModel.getColumn(entry.getKey());
507 columnMap.put(propName, column);
518 if (rootNode.getChildren().getNodesCount() != 0) {
519 final Graphics graphics = outlineView.getGraphics();
521 if (graphics != null) {
523 double outlineViewWidth = outlineView.getSize().getWidth();
525 List<Integer> columnWidths =
new ArrayList<>();
526 final FontMetrics metrics = graphics.getFontMetrics();
531 int totalColumnWidth = 0;
532 int cntMaxSizeColumns = 0;
536 for (
int column = 0; column < outline.getModel().getColumnCount(); column++) {
537 int firstColumnPadding = (column == 0) ? 32 : 0;
538 int columnWidthLimit = (column == 0) ? 350 : 300;
542 for (
int row = 0; row < Math.min(100, outline.getRowCount()); row++) {
543 TableCellRenderer renderer = outline.getCellRenderer(row, column);
544 Component comp = outline.prepareRenderer(renderer, row, column);
545 valuesWidth = Math.max(comp.getPreferredSize().width, valuesWidth);
548 int headerWidth = metrics.stringWidth(outline.getColumnName(column));
549 valuesWidth += firstColumnPadding;
551 int columnWidth = Math.max(valuesWidth, headerWidth);
552 columnWidth += 2 * margin + padding;
554 columnWidth = Math.min(columnWidth, columnWidthLimit);
555 columnWidths.add(columnWidth);
557 totalColumnWidth += columnWidth;
559 if (columnWidth == columnWidthLimit) {
571 if (totalColumnWidth < outlineViewWidth) {
572 if (cntMaxSizeColumns > 0) {
573 extraWidth = (int) ((outlineViewWidth - totalColumnWidth) / cntMaxSizeColumns);
575 extraWidth = (int) ((outlineViewWidth - totalColumnWidth) / columnWidths.size());
579 for (
int column = 0; column < columnWidths.size(); column++) {
580 int columnWidth = columnWidths.get(column);
582 if (cntMaxSizeColumns > 0) {
583 if (columnWidth >= ((column == 0) ? 350 : 300)) {
584 columnWidth += extraWidth;
587 columnWidth += extraWidth;
590 outline.getColumnModel().getColumn(column).setPreferredWidth(columnWidth);
595 outline.setAutoResizeMode(JTable.AUTO_RESIZE_ALL_COLUMNS);
600 return outline.getColumnModel();
608 String[] propStrings =
new String[props.size() * 2];
609 for (
int i = 0; i < props.size(); i++) {
610 final Property<?> prop = props.get(i);
611 prop.setValue(
"ComparableColumnTTV", Boolean.TRUE);
614 prop.setValue(
"TreeColumnTTV", Boolean.TRUE);
615 prop.setValue(
"SortingColumnTTV", Boolean.TRUE);
617 propStrings[2 * i] = prop.getName();
618 propStrings[2 * i + 1] = prop.getDisplayName();
620 outlineView.setPropertyColumns(propStrings);
628 if (rootNode == null || propertiesMap.isEmpty()) {
632 TableFilterNode tfn = (TableFilterNode) rootNode;
634 final ETableColumnModel columnModel = (ETableColumnModel) outline.getColumnModel();
635 for (Map.Entry<String, ETableColumn> entry : columnMap.entrySet()) {
636 String columnName = entry.getKey();
637 final String columnHiddenKey = ResultViewerPersistence.getColumnHiddenKey(tfn, columnName);
638 final TableColumn column = entry.getValue();
639 boolean columnHidden = columnModel.isColumnHidden(column);
641 preferences.putBoolean(columnHiddenKey,
true);
643 preferences.remove(columnHiddenKey);
654 if (rootNode == null || propertiesMap.isEmpty()) {
658 TableFilterNode tfn = (TableFilterNode) rootNode;
661 for (Map.Entry<Integer, Property<?>> entry : propertiesMap.entrySet()) {
662 preferences.putInt(ResultViewerPersistence.getColumnPositionKey(tfn, entry.getValue().getName()), entry.getKey());
671 if (rootNode == null || propertiesMap.isEmpty()) {
675 final TableFilterNode tfn = ((TableFilterNode) rootNode);
677 ETableColumnModel columnModel = (ETableColumnModel) outline.getColumnModel();
678 for (Map.Entry<String, ETableColumn> entry : columnMap.entrySet()) {
679 ETableColumn etc = entry.getValue();
680 String columnName = entry.getKey();
682 final String columnSortOrderKey = ResultViewerPersistence.getColumnSortOrderKey(tfn, columnName);
683 final String columnSortRankKey = ResultViewerPersistence.getColumnSortRankKey(tfn, columnName);
684 if (etc.isSorted() && (columnModel.isColumnHidden(etc) ==
false)) {
685 preferences.putBoolean(columnSortOrderKey, etc.isAscending());
686 preferences.putInt(columnSortRankKey, etc.getSortRank());
688 columnModel.setColumnSorted(etc,
true, 0);
689 preferences.remove(columnSortOrderKey);
690 preferences.remove(columnSortRankKey);
703 if (rootNode == null || propertiesMap.isEmpty()) {
707 final TableFilterNode tfn = (TableFilterNode) rootNode;
710 TreeSet<ColumnSortInfo> sortInfos =
new TreeSet<>(Comparator.comparing(ColumnSortInfo::getRank));
711 propertiesMap.entrySet().stream().forEach(entry -> {
712 final String propName = entry.getValue().getName();
714 Integer sortRank = preferences.getInt(ResultViewerPersistence.getColumnSortRankKey(tfn, propName), 0);
716 Boolean sortOrder = preferences.getBoolean(ResultViewerPersistence.getColumnSortOrderKey(tfn, propName),
true);
717 sortInfos.add(
new ColumnSortInfo(entry.getKey(), sortRank, sortOrder));
720 sortInfos.forEach(sortInfo -> outline.setColumnSorted(sortInfo.modelIndex, sortInfo.order, sortInfo.rank));
729 if (rootNode == null || propertiesMap.isEmpty()) {
734 final TableFilterNode tfn = ((TableFilterNode) rootNode);
735 ETableColumnModel columnModel = (ETableColumnModel) outline.getColumnModel();
736 for (Map.Entry<Integer, Property<?>> entry : propertiesMap.entrySet()) {
737 final String propName = entry.getValue().getName();
738 boolean hidden = preferences.getBoolean(ResultViewerPersistence.getColumnHiddenKey(tfn, propName),
false);
739 final TableColumn column = columnMap.get(propName);
740 columnModel.setColumnHidden(column, hidden);
755 List<Property<?>> props = ResultViewerPersistence.getAllChildProperties(rootNode, 100);
762 final TableFilterNode tfn = ((TableFilterNode) rootNode);
763 propertiesMap.clear();
771 int offset = props.size();
775 for (Property<?> prop : props) {
776 Integer value = preferences.getInt(ResultViewerPersistence.getColumnPositionKey(tfn, prop.getName()), -1);
777 if (value >= 0 && value < offset && !propertiesMap.containsKey(value)) {
778 propertiesMap.put(value, prop);
780 propertiesMap.put(offset, prop);
790 compactPropertiesMap();
792 return new ArrayList<>(propertiesMap.values());
802 int size = propertiesMap.size();
803 Queue<Integer> availablePositions =
new LinkedList<>();
804 for (
int i = 0; i < size; i++) {
805 if (!propertiesMap.containsKey(i)) {
806 availablePositions.add(i);
811 if (availablePositions.isEmpty()) {
818 ArrayList<Integer> keys =
new ArrayList<>(propertiesMap.keySet());
819 for (
int key : keys) {
821 propertiesMap.put(availablePositions.remove(), propertiesMap.remove(key));
832 this.outlineView.removeAll();
833 this.outlineView = null;
834 super.clearComponent();
847 this.modelIndex = modelIndex;
871 this.nodeName = nodeName;
876 if (!nodeName.isEmpty()) {
884 postPageChangeEvent();
887 void previousPage() {
889 postPageChangeEvent();
892 @NbBundle.Messages({
"# {0} - totalPages",
893 "DataResultViewerTable.goToPageTextField.msgDlg=Please enter a valid page number between 1 and {0}",
894 "DataResultViewerTable.goToPageTextField.err=Invalid page number"})
896 int originalPage = currentPage;
899 currentPage = Integer.decode(gotoPageTextField.getText());
900 }
catch (NumberFormatException e) {
905 if (currentPage > totalPages || currentPage < 1) {
906 currentPage = originalPage;
907 JOptionPane.showMessageDialog(DataResultViewerTable.this,
908 Bundle.DataResultViewerTable_goToPageTextField_msgDlg(totalPages),
909 Bundle.DataResultViewerTable_goToPageTextField_err(),
910 JOptionPane.WARNING_MESSAGE);
913 postPageChangeEvent();
920 void postPageChangeEvent() {
922 BaseChildFactory.post(nodeName,
new PageChangeEvent(currentPage));
923 }
catch (BaseChildFactory.NoSuchEventBusException ex) {
924 LOGGER.log(Level.WARNING,
"Failed to post page change event.", ex);
926 DataResultViewerTable.this.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
934 void postPageSizeChangeEvent() {
938 if (
this == pagingSupport) {
942 BaseChildFactory.post(nodeName,
new PageSizeChangeEvent(UserPreferences.getResultsTablePageSize()));
943 }
catch (BaseChildFactory.NoSuchEventBusException ex) {
944 LOGGER.log(Level.WARNING,
"Failed to post page size change event.", ex);
956 totalPages =
event.getPageCount();
957 if (totalPages > 1) {
959 togglePageControls(
true);
963 if (nodeName.equals(rootNode.getName())) {
975 pageLabel.setVisible(onOff);
976 pagesLabel.setVisible(onOff);
977 pagePrevButton.setVisible(onOff);
978 pageNextButton.setVisible(onOff);
979 pageNumLabel.setVisible(onOff);
980 gotoPageLabel.setVisible(onOff);
981 gotoPageTextField.setVisible(onOff);
982 gotoPageTextField.setVisible(onOff);
987 @NbBundle.Messages({
"# {0} - currentPage",
"# {1} - totalPages",
988 "DataResultViewerTable.pageNumbers.curOfTotal={0} of {1}"})
990 if (totalPages == 0) {
991 pagePrevButton.setEnabled(
false);
992 pageNextButton.setEnabled(
false);
993 pageNumLabel.setText(
"");
994 gotoPageTextField.setText(
"");
995 gotoPageTextField.setEnabled(
false);
997 pageNumLabel.setText(Bundle.DataResultViewerTable_pageNumbers_curOfTotal(Integer.toString(currentPage), Integer.toString(totalPages)));
999 pageNextButton.setEnabled(currentPage != totalPages);
1000 pagePrevButton.setEnabled(currentPage != 1);
1001 gotoPageTextField.setEnabled(totalPages > 1);
1002 gotoPageTextField.setText(
"");
1013 @NbBundle.Messages({
"DataResultViewerTable.commentRender.name=C",
1014 "DataResultViewerTable.commentRender.toolTip=C(omments) indicates whether the item has a comment",
1015 "DataResultViewerTable.scoreRender.name=S",
1016 "DataResultViewerTable.scoreRender.toolTip=S(core) indicates whether the item is interesting or notable",
1017 "DataResultViewerTable.countRender.name=O",
1018 "DataResultViewerTable.countRender.toolTip=O(ccurrences) indicates the number of data sources containing the item in the Central Repository"})
1021 if (e.getSource() instanceof ETableColumnModel) {
1022 TableColumn column = ((TableColumnModel) e.getSource()).getColumn(e.getToIndex());
1023 if (column.getHeaderValue().toString().equals(Bundle.DataResultViewerTable_commentRender_name())) {
1025 outlineView.setPropertyColumnDescription(column.getHeaderValue().toString(), Bundle.DataResultViewerTable_commentRender_toolTip());
1027 }
else if (column.getHeaderValue().toString().equals(Bundle.DataResultViewerTable_scoreRender_name())) {
1029 outlineView.setPropertyColumnDescription(column.getHeaderValue().toString(), Bundle.DataResultViewerTable_scoreRender_toolTip());
1031 }
else if (column.getHeaderValue().toString().equals(Bundle.DataResultViewerTable_countRender_name())) {
1032 outlineView.setPropertyColumnDescription(column.getHeaderValue().toString(), Bundle.DataResultViewerTable_countRender_toolTip());
1068 private class TableListener extends MouseAdapter implements TableColumnModelListener {
1072 private int startColumnIndex = -1;
1073 private int endColumnIndex = -1;
1078 int fromIndex = e.getFromIndex();
1079 int toIndex = e.getToIndex();
1080 if (fromIndex == toIndex) {
1094 if (startColumnIndex == -1) {
1095 startColumnIndex = fromIndex;
1097 endColumnIndex = toIndex;
1100 ArrayList<Integer> indicesList =
new ArrayList<>(propertiesMap.keySet());
1101 int leftIndex = Math.min(fromIndex, toIndex);
1102 int rightIndex = Math.max(fromIndex, toIndex);
1105 List<Integer> range = indicesList.subList(leftIndex, rightIndex + 1);
1106 int rangeSize = range.size();
1108 if (fromIndex < toIndex) {
1111 Property<?> movedProp = propertiesMap.get(range.get(0));
1112 for (
int i = 0; i < rangeSize - 1; i++) {
1113 propertiesMap.put(range.get(i), propertiesMap.get(range.get(i + 1)));
1115 propertiesMap.put(range.get(rangeSize - 1), movedProp);
1119 Property<?> movedProp = propertiesMap.get(range.get(rangeSize - 1));
1120 for (
int i = rangeSize - 1; i > 0; i--) {
1121 propertiesMap.put(range.get(i), propertiesMap.get(range.get(i - 1)));
1123 propertiesMap.put(range.get(0), movedProp);
1142 if (startColumnIndex != -1 && (startColumnIndex == 0 || endColumnIndex == 0)) {
1143 outline.moveColumn(endColumnIndex, startColumnIndex);
1145 startColumnIndex = -1;
1151 storeColumnSorting();
1156 columnAddedOrRemoved();
1161 columnAddedOrRemoved();
1170 if (listenToVisibilitEvents) {
1194 this.listenToVisibilitEvents = b;
1204 private static final long serialVersionUID = 1L;
1206 @NbBundle.Messages({
"DataResultViewerTable.commentRenderer.crComment.toolTip=Comment exists in Central Repository",
1207 "DataResultViewerTable.commentRenderer.tagComment.toolTip=Comment exists on associated tag(s)",
1208 "DataResultViewerTable.commentRenderer.crAndTagComment.toolTip=Comments exist both in Central Repository and on associated tag(s)",
1209 "DataResultViewerTable.commentRenderer.noComment.toolTip=No comments found"})
1212 Component component = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
1213 setBackground(component.getBackground());
1214 setHorizontalAlignment(CENTER);
1215 Object switchValue = null;
1219 switchValue = ((Node.Property) value).getValue();
1220 }
catch (IllegalAccessException | InvocationTargetException ex) {
1225 switchValue = value;
1230 switch ((HasCommentStatus) switchValue) {
1232 setIcon(COMMENT_ICON);
1233 setToolTipText(Bundle.DataResultViewerTable_commentRenderer_crComment_toolTip());
1236 setIcon(COMMENT_ICON);
1237 setToolTipText(Bundle.DataResultViewerTable_commentRenderer_tagComment_toolTip());
1239 case CR_AND_TAG_COMMENTS:
1240 setIcon(COMMENT_ICON);
1241 setToolTipText(Bundle.DataResultViewerTable_commentRenderer_crAndTagComment_toolTip());
1243 case TAG_NO_COMMENT:
1247 setToolTipText(Bundle.DataResultViewerTable_commentRenderer_noComment_toolTip());
1264 private static final long serialVersionUID = 1L;
1268 Component component = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
1269 setBackground(component.getBackground());
1270 setHorizontalAlignment(CENTER);
1271 Object switchValue = null;
1275 switchValue = ((Node.Property) value).getValue();
1276 setToolTipText(((FeatureDescriptor) value).getShortDescription());
1277 }
catch (IllegalAccessException | InvocationTargetException ex) {
1283 switchValue = value;
1286 if ((switchValue instanceof
Score)) {
1288 switch ((Score) switchValue) {
1289 case INTERESTING_SCORE:
1290 setIcon(INTERESTING_SCORE_ICON);
1293 setIcon(NOTABLE_ICON_SCORE);
1313 private static final long serialVersionUID = 1L;
1317 Component component = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
1318 setBackground(component.getBackground());
1319 setHorizontalAlignment(LEFT);
1320 Object countValue = null;
1324 countValue = ((Node.Property) value).getValue();
1325 setToolTipText(((FeatureDescriptor) value).getShortDescription());
1326 }
catch (IllegalAccessException | InvocationTargetException ex) {
1334 if ((countValue instanceof Long)) {
1336 if ((Long) countValue >= 0) {
1337 setText(countValue.toString());
1371 @SuppressWarnings(
"unchecked")
1373 private
void initComponents() {
1375 pageLabel =
new javax.swing.JLabel();
1376 pageNumLabel =
new javax.swing.JLabel();
1377 pagesLabel =
new javax.swing.JLabel();
1378 pagePrevButton =
new javax.swing.JButton();
1379 pageNextButton =
new javax.swing.JButton();
1381 gotoPageLabel =
new javax.swing.JLabel();
1382 gotoPageTextField =
new javax.swing.JTextField();
1383 exportCSVButton =
new javax.swing.JButton();
1385 pageLabel.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.pageLabel.text"));
1387 pageNumLabel.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.pageNumLabel.text"));
1389 pagesLabel.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.pagesLabel.text"));
1391 pagePrevButton.setIcon(
new javax.swing.ImageIcon(getClass().getResource(
"/org/sleuthkit/autopsy/corecomponents/btn_step_back.png")));
1392 pagePrevButton.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.pagePrevButton.text"));
1393 pagePrevButton.setDisabledIcon(
new javax.swing.ImageIcon(getClass().getResource(
"/org/sleuthkit/autopsy/corecomponents/btn_step_back_disabled.png")));
1394 pagePrevButton.setFocusable(
false);
1395 pagePrevButton.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER);
1396 pagePrevButton.setMargin(
new java.awt.Insets(2, 0, 2, 0));
1397 pagePrevButton.setPreferredSize(
new java.awt.Dimension(55, 23));
1398 pagePrevButton.setRolloverIcon(
new javax.swing.ImageIcon(getClass().getResource(
"/org/sleuthkit/autopsy/corecomponents/btn_step_back_hover.png")));
1399 pagePrevButton.setVerticalTextPosition(javax.swing.SwingConstants.BOTTOM);
1400 pagePrevButton.addActionListener(
new java.awt.event.ActionListener() {
1401 public void actionPerformed(java.awt.event.ActionEvent evt) {
1402 pagePrevButtonActionPerformed(evt);
1406 pageNextButton.setIcon(
new javax.swing.ImageIcon(getClass().getResource(
"/org/sleuthkit/autopsy/corecomponents/btn_step_forward.png")));
1407 pageNextButton.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.pageNextButton.text"));
1408 pageNextButton.setDisabledIcon(
new javax.swing.ImageIcon(getClass().getResource(
"/org/sleuthkit/autopsy/corecomponents/btn_step_forward_disabled.png")));
1409 pageNextButton.setFocusable(
false);
1410 pageNextButton.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER);
1411 pageNextButton.setMargin(
new java.awt.Insets(2, 0, 2, 0));
1412 pageNextButton.setMaximumSize(
new java.awt.Dimension(27, 23));
1413 pageNextButton.setMinimumSize(
new java.awt.Dimension(27, 23));
1414 pageNextButton.setRolloverIcon(
new javax.swing.ImageIcon(getClass().getResource(
"/org/sleuthkit/autopsy/corecomponents/btn_step_forward_hover.png")));
1415 pageNextButton.setVerticalTextPosition(javax.swing.SwingConstants.BOTTOM);
1416 pageNextButton.addActionListener(
new java.awt.event.ActionListener() {
1417 public void actionPerformed(java.awt.event.ActionEvent evt) {
1418 pageNextButtonActionPerformed(evt);
1422 gotoPageLabel.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.gotoPageLabel.text"));
1424 gotoPageTextField.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.gotoPageTextField.text"));
1425 gotoPageTextField.addActionListener(
new java.awt.event.ActionListener() {
1426 public void actionPerformed(java.awt.event.ActionEvent evt) {
1427 gotoPageTextFieldActionPerformed(evt);
1431 exportCSVButton.setText(
org.openide.util.NbBundle.getMessage(
DataResultViewerTable.class,
"DataResultViewerTable.exportCSVButton.text"));
1432 exportCSVButton.addActionListener(
new java.awt.event.ActionListener() {
1433 public void actionPerformed(java.awt.event.ActionEvent evt) {
1434 exportCSVButtonActionPerformed(evt);
1438 javax.swing.GroupLayout layout =
new javax.swing.GroupLayout(
this);
1439 this.setLayout(layout);
1440 layout.setHorizontalGroup(
1441 layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
1442 .addComponent(outlineView, javax.swing.GroupLayout.DEFAULT_SIZE, 904, Short.MAX_VALUE)
1443 .addGroup(layout.createSequentialGroup()
1445 .addComponent(pageLabel)
1446 .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
1447 .addComponent(pageNumLabel, javax.swing.GroupLayout.PREFERRED_SIZE, 53, javax.swing.GroupLayout.PREFERRED_SIZE)
1449 .addComponent(pagesLabel)
1450 .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
1451 .addComponent(pagePrevButton, javax.swing.GroupLayout.PREFERRED_SIZE, 16, javax.swing.GroupLayout.PREFERRED_SIZE)
1452 .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
1453 .addComponent(pageNextButton, javax.swing.GroupLayout.PREFERRED_SIZE, 16, javax.swing.GroupLayout.PREFERRED_SIZE)
1454 .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
1455 .addComponent(gotoPageLabel)
1456 .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
1457 .addComponent(gotoPageTextField, javax.swing.GroupLayout.PREFERRED_SIZE, 33, javax.swing.GroupLayout.PREFERRED_SIZE)
1458 .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
1459 .addComponent(exportCSVButton))
1462 layout.linkSize(javax.swing.SwingConstants.HORIZONTAL,
new java.awt.Component[] {pageNextButton, pagePrevButton});
1464 layout.setVerticalGroup(
1465 layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
1466 .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
1468 .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.CENTER)
1469 .addComponent(pageLabel)
1470 .addComponent(pageNumLabel)
1471 .addComponent(pagesLabel)
1472 .addComponent(pagePrevButton, javax.swing.GroupLayout.PREFERRED_SIZE, 14, javax.swing.GroupLayout.PREFERRED_SIZE)
1473 .addComponent(pageNextButton, javax.swing.GroupLayout.PREFERRED_SIZE, 15, javax.swing.GroupLayout.PREFERRED_SIZE)
1474 .addComponent(gotoPageLabel)
1475 .addComponent(gotoPageTextField, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
1476 .addComponent(exportCSVButton))
1478 .addComponent(outlineView, javax.swing.GroupLayout.DEFAULT_SIZE, 321, Short.MAX_VALUE)
1482 layout.linkSize(javax.swing.SwingConstants.VERTICAL,
new java.awt.Component[] {pageNextButton, pagePrevButton});
1484 gotoPageLabel.getAccessibleContext().setAccessibleName(
"");
1488 pagingSupport.previousPage();
1492 pagingSupport.nextPage();
1496 pagingSupport.gotoPage();
1499 @NbBundle.Messages({
"DataResultViewerTable.exportCSVButtonActionPerformed.empty=No data to export"
1502 Node currentRoot = this.getExplorerManager().getRootContext();
1503 if (currentRoot != null && currentRoot.getChildren().getNodesCount() > 0) {
javax.swing.JLabel pageLabel
void mouseReleased(MouseEvent e)
boolean matches(Node candidateNode)
javax.swing.JLabel pageNumLabel
Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)
TableColumnModel getColumnModel()
final Map< String, ETableColumn > columnMap
Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)
org.openide.explorer.view.OutlineView outlineView
void compactPropertiesMap()
void columnRemoved(TableColumnModelEvent e)
void columnAdded(TableColumnModelEvent e)
synchronized List< Node.Property<?> > loadColumnOrder()
synchronized void storeColumnVisibility()
void pageNextButtonActionPerformed(java.awt.event.ActionEvent evt)
void subscribeToPageCountChange(PageCountChangeEvent event)
static void register(String nodeName, Object subscriber)
synchronized void storeColumnSorting()
javax.swing.JButton pageNextButton
synchronized void assignColumns(List< Property<?>> props)
final IconRendererTableListener iconRendererListener
void columnMarginChanged(ChangeEvent e)
static final String FIRST_COLUMN_LABEL
void mouseClicked(MouseEvent e)
void columnSelectionChanged(ListSelectionEvent e)
void columnRemoved(TableColumnModelEvent e)
javax.swing.JTextField gotoPageTextField
final TableListener outlineViewListener
void columnAddedOrRemoved()
void exportCSVButtonActionPerformed(java.awt.event.ActionEvent evt)
boolean listenToVisibilitEvents
void columnMoved(TableColumnModelEvent e)
DataResultViewer createInstance()
javax.swing.JLabel gotoPageLabel
static final String RESULTS_TABLE_PAGE_SIZE
final Map< Integer, Property<?> > propertiesMap
void gotoPageTextFieldActionPerformed(java.awt.event.ActionEvent evt)
void columnSelectionChanged(ListSelectionEvent e)
javax.swing.JButton pagePrevButton
javax.swing.JLabel pagesLabel
synchronized void loadColumnVisibility()
ColumnSortInfo(int modelIndex, int rank, boolean order)
void addTreeExpansionListener(TreeExpansionListener listener)
void listenToVisibilityChanges(boolean b)
synchronized static Logger getLogger(String name)
synchronized void loadColumnSorting()
static void addChangeListener(PreferenceChangeListener listener)
void pagePrevButtonActionPerformed(java.awt.event.ActionEvent evt)
void initializePagingSupport()
static void info(String message)
void columnMoved(TableColumnModelEvent e)
javax.swing.JButton exportCSVButton
DataResultViewerTable(ExplorerManager explorerManager)
void columnMarginChanged(ChangeEvent e)
boolean isSupported(Node candidateRootNode)
static void saveNodesToCSV(Collection<?extends Node > nodesToExport, Component component)
void columnAdded(TableColumnModelEvent e)
synchronized void storeColumnOrder()
DataResultViewerTable(ExplorerManager explorerManager, String title)
void togglePageControls(boolean onOff)