diff --git a/Core/src/org/sleuthkit/autopsy/corecomponents/DataResultViewerThumbnail.java b/Core/src/org/sleuthkit/autopsy/corecomponents/DataResultViewerThumbnail.java index c0398ffe27..f1e790f0f8 100644 --- a/Core/src/org/sleuthkit/autopsy/corecomponents/DataResultViewerThumbnail.java +++ b/Core/src/org/sleuthkit/autopsy/corecomponents/DataResultViewerThumbnail.java @@ -296,14 +296,7 @@ final class DataResultViewerThumbnail extends AbstractDataResultViewer { if (selectedNode == null) { return false; } - - Children ch = selectedNode.getChildren(); - for (Node n : ch.getNodes()) { - if (ThumbnailViewChildren.isSupported(n)) { - return true; - } - } - return false; + return true; } @Override diff --git a/Core/src/org/sleuthkit/autopsy/modules/hashdatabase/HashDbIngestModule.java b/Core/src/org/sleuthkit/autopsy/modules/hashdatabase/HashDbIngestModule.java index 061d0ff602..8bdb597c25 100644 --- a/Core/src/org/sleuthkit/autopsy/modules/hashdatabase/HashDbIngestModule.java +++ b/Core/src/org/sleuthkit/autopsy/modules/hashdatabase/HashDbIngestModule.java @@ -331,7 +331,8 @@ public class HashDbIngestModule implements FileIngestModule { } } - private synchronized void postSummary() { + private static synchronized void postSummary(long jobId, + List knownBadHashSets, List knownHashSets) { IngestJobTotals jobTotals = totalsForIngestJobs.remove(jobId); if ((!knownBadHashSets.isEmpty()) || (!knownHashSets.isEmpty())) { @@ -340,20 +341,20 @@ public class HashDbIngestModule implements FileIngestModule { detailsSb.append(""); //NON-NLS detailsSb.append(""); //NON-NLS detailsSb.append(""); //NON-NLS detailsSb.append("\n"); //NON-NLS detailsSb.append("\n"); //NON-NLS detailsSb.append("
") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "HashDbIngestModule.complete.knownBadsFound")) + .append(NbBundle.getMessage(HashDbIngestModule.class, "HashDbIngestModule.complete.knownBadsFound")) .append("").append(jobTotals.totalKnownBadCount.get()).append("
") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "HashDbIngestModule.complete.totalCalcTime")) + .append(NbBundle.getMessage(HashDbIngestModule.class, "HashDbIngestModule.complete.totalCalcTime")) .append("").append(jobTotals.totalCalctime.get()).append("
") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "HashDbIngestModule.complete.totalLookupTime")) + .append(NbBundle.getMessage(HashDbIngestModule.class, "HashDbIngestModule.complete.totalLookupTime")) .append("").append(jobTotals.totalLookuptime.get()).append("
"); //NON-NLS detailsSb.append("

") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "HashDbIngestModule.complete.databasesUsed")) + .append(NbBundle.getMessage(HashDbIngestModule.class, "HashDbIngestModule.complete.databasesUsed")) .append("

\n"); //NON-NLS - services.postMessage(IngestMessage.createMessage( + IngestServices.getInstance().postMessage(IngestMessage.createMessage( IngestMessage.MessageType.INFO, HashLookupModuleFactory.getModuleName(), - NbBundle.getMessage(this.getClass(), + NbBundle.getMessage(HashDbIngestModule.class, "HashDbIngestModule.complete.hashLookupResults"), detailsSb.toString())); } @@ -373,7 +374,7 @@ public class HashDbIngestModule implements FileIngestModule { @Override public void shutDown() { if (refCounter.decrementAndGet(jobId) == 0) { - postSummary(); + postSummary(jobId, knownBadHashSets, knownHashSets); } } } diff --git a/Core/src/org/sleuthkit/autopsy/modules/photoreccarver/PhotoRecCarverFileIngestModule.java b/Core/src/org/sleuthkit/autopsy/modules/photoreccarver/PhotoRecCarverFileIngestModule.java index e0277e524a..1ab4204caf 100755 --- a/Core/src/org/sleuthkit/autopsy/modules/photoreccarver/PhotoRecCarverFileIngestModule.java +++ b/Core/src/org/sleuthkit/autopsy/modules/photoreccarver/PhotoRecCarverFileIngestModule.java @@ -98,6 +98,11 @@ final class PhotoRecCarverFileIngestModule implements FileIngestModule { } return totals; } + + private static synchronized void initTotalsForIngestJob(long ingestJobId) { + IngestJobTotals totals = new PhotoRecCarverFileIngestModule.IngestJobTotals(); + totalsForIngestJobs.put(ingestJobId, totals); + } /** * @inheritDoc @@ -136,6 +141,9 @@ final class PhotoRecCarverFileIngestModule implements FileIngestModule { // Save the directories for the current job. PhotoRecCarverFileIngestModule.pathsByJob.put(this.jobId, new WorkingPaths(outputDirPath, tempDirPath)); + + // Initialize job totals + initTotalsForIngestJob(jobId); } catch (SecurityException | IOException | UnsupportedOperationException ex) { throw new IngestModule.IngestModuleException(NbBundle.getMessage(this.getClass(), "cannotCreateOutputDir.message", ex.getLocalizedMessage())); } @@ -271,7 +279,7 @@ final class PhotoRecCarverFileIngestModule implements FileIngestModule { } } - private synchronized void postSummary() { + private static synchronized void postSummary(long jobId) { IngestJobTotals jobTotals = totalsForIngestJobs.remove(jobId); StringBuilder detailsSb = new StringBuilder(); @@ -279,22 +287,22 @@ final class PhotoRecCarverFileIngestModule implements FileIngestModule { detailsSb.append(""); //NON-NLS detailsSb.append(""); //NON-NLS detailsSb.append(""); //NON-NLS detailsSb.append("\n"); //NON-NLS detailsSb.append("\n"); //NON-NLS detailsSb.append("
") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "PhotoRecIngestModule.complete.numberOfCarved")) + .append(NbBundle.getMessage(PhotoRecCarverFileIngestModule.class, "PhotoRecIngestModule.complete.numberOfCarved")) .append("").append(jobTotals.totalItemsRecovered.get()).append("
") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "PhotoRecIngestModule.complete.totalWritetime")) + .append(NbBundle.getMessage(PhotoRecCarverFileIngestModule.class, "PhotoRecIngestModule.complete.totalWritetime")) .append("").append(jobTotals.totalWritetime.get()).append("
") //NON-NLS - .append(NbBundle.getMessage(this.getClass(), "PhotoRecIngestModule.complete.totalParsetime")) + .append(NbBundle.getMessage(PhotoRecCarverFileIngestModule.class, "PhotoRecIngestModule.complete.totalParsetime")) .append("").append(jobTotals.totalParsetime.get()).append("
"); //NON-NLS - services.postMessage(IngestMessage.createMessage( + IngestServices.getInstance().postMessage(IngestMessage.createMessage( IngestMessage.MessageType.INFO, PhotoRecCarverIngestModuleFactory.getModuleName(), - NbBundle.getMessage(this.getClass(), + NbBundle.getMessage(PhotoRecCarverFileIngestModule.class, "PhotoRecIngestModule.complete.photoRecResults"), detailsSb.toString())); @@ -311,7 +319,7 @@ final class PhotoRecCarverFileIngestModule implements FileIngestModule { // the working paths map entry for the job and deletes the temp dir. WorkingPaths paths = PhotoRecCarverFileIngestModule.pathsByJob.remove(this.jobId); FileUtil.deleteDir(new File(paths.getTempDirPath().toString())); - postSummary(); + postSummary(jobId); } catch (SecurityException ex) { logger.log(Level.SEVERE, "Error shutting down PhotoRec carver module", ex); // NON-NLS diff --git a/ImageGallery/nbproject/project.xml b/ImageGallery/nbproject/project.xml index ab6cd75280..337b411e37 100644 --- a/ImageGallery/nbproject/project.xml +++ b/ImageGallery/nbproject/project.xml @@ -4,7 +4,7 @@ org.sleuthkit.autopsy.imagegallery - + org.netbeans.api.progress @@ -103,7 +103,7 @@ 10 - 10.0.11 + 10.3 diff --git a/ImageGallery/nbproject/suite.properties b/ImageGallery/nbproject/suite.properties new file mode 100644 index 0000000000..29d7cc9bd6 --- /dev/null +++ b/ImageGallery/nbproject/suite.properties @@ -0,0 +1 @@ +suite.dir=${basedir}/.. diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/FXMLConstructor.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/FXMLConstructor.java index 7dc9a86757..3b0a1dd4c8 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/FXMLConstructor.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/FXMLConstructor.java @@ -1,7 +1,7 @@ /* * Autopsy Forensic Browser * - * Copyright 2013 Basis Technology Corp. + * Copyright 2013-15 Basis Technology Corp. * Contact: carrier sleuthkit org * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -60,4 +60,7 @@ public class FXMLConstructor { } } + + private FXMLConstructor() { + } } diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableAttribute.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableAttribute.java index 495aabf70f..48f580266d 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableAttribute.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableAttribute.java @@ -1,7 +1,7 @@ /* * Autopsy Forensic Browser * - * Copyright 2013 Basis Technology Corp. + * Copyright 2013-15 Basis Technology Corp. * Contact: carrier sleuthkit org * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -39,6 +39,9 @@ import org.sleuthkit.datamodel.TagName; */ public class DrawableAttribute> { + public final static DrawableAttribute MD5_HASH + = new DrawableAttribute<>(AttributeName.MD5_HASH, "MD5 Hash", false, "icon-hashtag.png", f -> Collections.singleton(f.getMd5Hash())); + public final static DrawableAttribute NAME = new DrawableAttribute<>(AttributeName.NAME, "Name", true, "folder-rename.png", f -> Collections.singleton(f.getName())); @@ -50,8 +53,8 @@ public class DrawableAttribute> { * in the DrawableDB. they have special code in various places to make this * transparent. * - * //TODO: this had lead to awkward hard to maintain code, and little - * advantage. move categories into DrawableDB + * //TODO: this has lead to awkward hard to maintain code, and little + * advantage. move categories into DrawableDB? */ public final static DrawableAttribute CATEGORY = new DrawableAttribute<>(AttributeName.CATEGORY, "Category", false, "category-icon.png", f -> Collections.singleton(f.getCategory())); @@ -91,7 +94,7 @@ public class DrawableAttribute> { final private static List> values = Arrays.asList(NAME, ANALYZED, CATEGORY, TAGS, PATH, CREATED_TIME, - MODIFIED_TIME, HASHSET, MAKE, MODEL, OBJ_ID, WIDTH, HEIGHT); + MODIFIED_TIME, MD5_HASH, HASHSET, MAKE, MODEL, OBJ_ID, WIDTH, HEIGHT); private final Function, Collection> extractor; @@ -123,7 +126,7 @@ public class DrawableAttribute> { } public static List> getGroupableAttrs() { - return groupables; + return Collections.unmodifiableList(groupables); } public static List> getValues() { @@ -152,7 +155,8 @@ public class DrawableAttribute> { HASHSET, OBJ_ID, WIDTH, - HEIGHT; + HEIGHT, + MD5_HASH; } public Collection getValue(DrawableFile f) { diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableFile.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableFile.java index da58bd07bf..80519e8b82 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableFile.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/DrawableFile.java @@ -1,7 +1,7 @@ /* * Autopsy Forensic Browser * - * Copyright 2013 Basis Technology Corp. + * Copyright 2013-15 Basis Technology Corp. * Contact: carrier sleuthkit org * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -29,8 +29,6 @@ import java.util.logging.Level; import java.util.stream.Collectors; import javafx.beans.property.SimpleBooleanProperty; import javafx.beans.property.SimpleObjectProperty; -import javafx.collections.FXCollections; -import javafx.collections.ObservableList; import javafx.scene.image.Image; import javafx.util.Pair; import org.apache.commons.lang3.StringUtils; @@ -92,7 +90,7 @@ public abstract class DrawableFile extends AbstractFile private String drawablePath; - protected T file; + private final T file; private final SimpleBooleanProperty analyzed; @@ -145,12 +143,14 @@ public abstract class DrawableFile extends AbstractFile return new ArrayList<>(); } - public ObservableList, ? extends Object>> getAttributesList() { - final ObservableList, ? extends Object>> attributeList = FXCollections.observableArrayList(); - for (DrawableAttribute attr : DrawableAttribute.getValues()) { - attributeList.add(new Pair<>(attr, attr.getValue(this))); - } - return attributeList; + public List, Collection>> getAttributesList() { + return DrawableAttribute.getValues().stream() + .map(this::makeAttributeValuePair) + .collect(Collectors.toList()); + } + + private Pair, Collection> makeAttributeValuePair(DrawableAttribute t) { + return new Pair<>(t, t.getValue(DrawableFile.this)); } public String getModel() { @@ -181,47 +181,6 @@ public abstract class DrawableFile extends AbstractFile return Collections.emptySet(); } - @Deprecated - protected final List getValuesOfBBAttribute(BlackboardArtifact.ARTIFACT_TYPE artType, BlackboardAttribute.ATTRIBUTE_TYPE attrType) { - ArrayList vals = new ArrayList<>(); - try { - //why doesn't file.getArtifacts() work? - //TODO: this seams like overkill, use a more targeted query - ArrayList artifacts = getAllArtifacts(); - - for (BlackboardArtifact artf : artifacts) { - if (artf.getArtifactTypeID() == artType.getTypeID()) { - for (BlackboardAttribute attr : artf.getAttributes()) { - if (attr.getAttributeTypeID() == attrType.getTypeID()) { - - switch (attr.getValueType()) { - case BYTE: - vals.add(attr.getValueBytes()); - break; - case DOUBLE: - vals.add(attr.getValueDouble()); - break; - case INTEGER: - vals.add(attr.getValueInt()); - break; - case LONG: - vals.add(attr.getValueLong()); - break; - case STRING: - vals.add(attr.getValueString()); - break; - } - } - } - } - } - } catch (TskCoreException ex) { - Logger.getAnonymousLogger().log(Level.WARNING, "problem looking up {0}/{1}" + " " + " for {2}", new Object[]{artType.getDisplayName(), attrType.getDisplayName(), getName()}); - } - - return vals; - } - protected Object getValueOfBBAttribute(BlackboardArtifact.ARTIFACT_TYPE artType, BlackboardAttribute.ATTRIBUTE_TYPE attrType) { try { diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/ImageFile.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/ImageFile.java index 2973a435ed..3bacff51c4 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/ImageFile.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/datamodel/ImageFile.java @@ -54,9 +54,9 @@ public class ImageFile extends DrawableFile { public Image getFullSizeImage() { Image image = (imageRef != null) ? imageRef.get() : null; if (image == null || image.isError()) { - if (FileTypeUtils.isGIF(file)) { + if (FileTypeUtils.isGIF(getAbstractFile())) { //directly read gif to preserve potential animation, - image = new Image(new BufferedInputStream(new ReadContentInputStream(file))); + image = new Image(new BufferedInputStream(new ReadContentInputStream(getAbstractFile()))); } } if (image == null || image.isError()) { diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/GuiUtils.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/GuiUtils.java index 4a2a84fd46..27651147cc 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/GuiUtils.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/GuiUtils.java @@ -25,6 +25,8 @@ import javafx.scene.control.SplitMenuButton; import javafx.scene.image.ImageView; import org.sleuthkit.autopsy.imagegallery.ImageGalleryController; import org.sleuthkit.autopsy.imagegallery.actions.AddDrawableTagAction; +import org.sleuthkit.autopsy.imagegallery.actions.CategorizeAction; +import org.sleuthkit.autopsy.imagegallery.datamodel.Category; import org.sleuthkit.autopsy.imagegallery.datamodel.DrawableAttribute; import org.sleuthkit.datamodel.TagName; @@ -56,6 +58,19 @@ public class GuiUtils { return menuItem; } + public static MenuItem createSelCatMenuItem(Category cat, final SplitMenuButton catSelectedMenuButton, ImageGalleryController controller) { + final MenuItem menuItem = new MenuItem(cat.getDisplayName(), new ImageView(DrawableAttribute.CATEGORY.getIcon())); + menuItem.setOnAction(new EventHandler() { + @Override + public void handle(ActionEvent t) { + new CategorizeAction(controller).addTag(controller.getTagsManager().getTagName(cat), ""); + catSelectedMenuButton.setText(cat.getDisplayName()); + catSelectedMenuButton.setOnAction(this); + } + }); + return menuItem; + } + private GuiUtils() { } diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/Toolbar.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/Toolbar.java index 43cb88d778..8f1f4466a2 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/Toolbar.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/Toolbar.java @@ -1,7 +1,7 @@ /* * Autopsy Forensic Browser * - * Copyright 2013 Basis Technology Corp. + * Copyright 2013-15 Basis Technology Corp. * Contact: carrier sleuthkit org * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -18,7 +18,11 @@ */ package org.sleuthkit.autopsy.imagegallery.gui; -import java.util.ArrayList; +import java.util.List; +import java.util.logging.Level; +import java.util.logging.Logger; +import java.util.stream.Collectors; +import java.util.stream.Stream; import javafx.application.Platform; import javafx.beans.InvalidationListener; import javafx.beans.Observable; @@ -27,7 +31,6 @@ import javafx.beans.property.SimpleObjectProperty; import javafx.beans.value.ObservableValue; import javafx.collections.FXCollections; import javafx.event.ActionEvent; -import javafx.event.EventHandler; import javafx.fxml.FXML; import javafx.scene.control.CheckBox; import javafx.scene.control.ComboBox; @@ -40,15 +43,12 @@ import javafx.scene.control.ToolBar; import javafx.scene.image.ImageView; import javafx.scene.layout.HBox; import javax.swing.SortOrder; -import org.openide.util.Exceptions; import org.sleuthkit.autopsy.imagegallery.FXMLConstructor; import org.sleuthkit.autopsy.imagegallery.FileIDSelectionModel; import org.sleuthkit.autopsy.imagegallery.ImageGalleryController; -import org.sleuthkit.autopsy.imagegallery.actions.CategorizeAction; import org.sleuthkit.autopsy.imagegallery.datamodel.Category; import org.sleuthkit.autopsy.imagegallery.datamodel.DrawableAttribute; import org.sleuthkit.autopsy.imagegallery.datamodel.grouping.GroupSortBy; -import org.sleuthkit.datamodel.TagName; import org.sleuthkit.datamodel.TskCoreException; /** @@ -56,6 +56,8 @@ import org.sleuthkit.datamodel.TskCoreException; */ public class Toolbar extends ToolBar { + private static final Logger LOGGER = Logger.getLogger(Toolbar.class.getName()); + private static final int SIZE_SLIDER_DEFAULT = 100; @FXML @@ -79,8 +81,6 @@ public class Toolbar extends ToolBar { @FXML private ToggleGroup orderGroup; -// @FXML -// private ToggleButton metaDataToggle; @FXML private HBox sortControlGroup; @@ -103,15 +103,12 @@ public class Toolbar extends ToolBar { ImageGalleryController.getDefault().getGroupManager().regroup(groupByBox.getSelectionModel().getSelectedItem(), sortByBox.getSelectionModel().getSelectedItem(), getSortOrder(), false); }; - private ImageGalleryController controller; + private final ImageGalleryController controller; synchronized public SortOrder getSortOrder() { return orderProperty.get(); } -// public ReadOnlyBooleanProperty showMetaDataProperty() { -// return metaDataToggle.selectedProperty(); -// } public DoubleProperty sizeSliderValue() { return sizeSlider.valueProperty(); } @@ -152,32 +149,28 @@ public class Toolbar extends ToolBar { try { GuiUtils.createSelTagMenuItem(getController().getTagsManager().getFollowUpTagName(), tagSelectedMenuButton, getController()).getOnAction().handle(t); } catch (TskCoreException ex) { - Exceptions.printStackTrace(ex); + LOGGER.log(Level.SEVERE, "Could create follow up tag menu item", ex); } }); tagSelectedMenuButton.setGraphic(new ImageView(DrawableAttribute.TAGS.getIcon())); tagSelectedMenuButton.showingProperty().addListener((ObservableValue ov, Boolean t, Boolean t1) -> { if (t1) { - ArrayList selTagMenues = new ArrayList<>(); - for (final TagName tn : getController().getTagsManager().getNonCategoryTagNames()) { - MenuItem menuItem = GuiUtils.createSelTagMenuItem(tn, tagSelectedMenuButton, getController()); - selTagMenues.add(menuItem); - } + List selTagMenues = getController().getTagsManager().getNonCategoryTagNames().stream() + .map(tn -> GuiUtils.createSelTagMenuItem(tn, tagSelectedMenuButton, getController())) + .collect(Collectors.toList()); tagSelectedMenuButton.getItems().setAll(selTagMenues); } }); - catSelectedMenuButton.setOnAction(createSelCatMenuItem(Category.FIVE, catSelectedMenuButton, getController()).getOnAction()); + catSelectedMenuButton.setOnAction(GuiUtils.createSelCatMenuItem(Category.FIVE, catSelectedMenuButton, getController()).getOnAction()); catSelectedMenuButton.setText(Category.FIVE.getDisplayName()); catSelectedMenuButton.setGraphic(new ImageView(DrawableAttribute.CATEGORY.getIcon())); catSelectedMenuButton.showingProperty().addListener((ObservableValue ov, Boolean t, Boolean t1) -> { if (t1) { - ArrayList categoryMenues = new ArrayList<>(); - for (final Category cat : Category.values()) { - MenuItem menuItem = createSelCatMenuItem(cat, catSelectedMenuButton, getController()); - categoryMenues.add(menuItem); - } + List categoryMenues = Stream.of(Category.values()) + .map((cat) -> GuiUtils.createSelCatMenuItem(cat, catSelectedMenuButton, getController())) + .collect(Collectors.toList()); catSelectedMenuButton.getItems().setAll(categoryMenues); } }); @@ -224,19 +217,6 @@ public class Toolbar extends ToolBar { FXMLConstructor.construct(this, "Toolbar.fxml"); } - private static MenuItem createSelCatMenuItem(Category cat, final SplitMenuButton catSelectedMenuButton, ImageGalleryController controller) { - final MenuItem menuItem = new MenuItem(cat.getDisplayName(), new ImageView(DrawableAttribute.CATEGORY.getIcon())); - menuItem.setOnAction(new EventHandler() { - @Override - public void handle(ActionEvent t) { - new CategorizeAction(controller).addTag(controller.getTagsManager().getTagName(cat), ""); - catSelectedMenuButton.setText(cat.getDisplayName()); - catSelectedMenuButton.setOnAction(this); - } - }); - return menuItem; - } - private ImageGalleryController getController() { return controller; } diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTile.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTile.java index 047243084d..35fad38576 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTile.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTile.java @@ -52,9 +52,8 @@ public class DrawableTile extends DrawableTileBase { @Override protected void initialize() { super.initialize(); - assert imageBorder != null : "fx:id=\"imageAnchor\" was not injected: check your FXML file 'DrawableTile.fxml'."; assert imageView != null : "fx:id=\"imageView\" was not injected: check your FXML file 'DrawableTile.fxml'."; - assert nameLabel != null : "fx:id=\"nameLabel\" was not injected: check your FXML file 'DrawableTile.fxml'."; + //set up properties and binding setCache(true); setCacheHint(CacheHint.SPEED); diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTileBase.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTileBase.java index 18270282a2..1bb1aa2ff2 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTileBase.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/DrawableTileBase.java @@ -70,13 +70,14 @@ import org.sleuthkit.autopsy.imagegallery.actions.SwingMenuItemAdapter; import org.sleuthkit.autopsy.imagegallery.datamodel.DrawableAttribute; import org.sleuthkit.autopsy.imagegallery.datamodel.DrawableFile; import org.sleuthkit.autopsy.imagegallery.datamodel.VideoFile; +import org.sleuthkit.autopsy.imagegallery.datamodel.grouping.GroupViewMode; import org.sleuthkit.datamodel.ContentTag; import org.sleuthkit.datamodel.TagName; import org.sleuthkit.datamodel.TskCoreException; /** * An abstract base class for {@link DrawableTile} and {@link SlideShowView}, - * since they share a similar node tree and many behaviors, other implementers + * since they share a similar node tree and many behaviors, other implementors * of {@link DrawableView}s should implement the interface directly * */ @@ -85,7 +86,6 @@ public abstract class DrawableTileBase extends DrawableUIBase { private static final Logger LOGGER = Logger.getLogger(DrawableTileBase.class.getName()); private static final Border UNSELECTED_BORDER = new Border(new BorderStroke(Color.GRAY, BorderStrokeStyle.SOLID, new CornerRadii(2), new BorderWidths(3))); - private static final Border SELECTED_BORDER = new Border(new BorderStroke(Color.BLUE, BorderStrokeStyle.SOLID, new CornerRadii(2), new BorderWidths(3))); //TODO: do this in CSS? -jm @@ -95,37 +95,29 @@ public abstract class DrawableTileBase extends DrawableUIBase { protected static final FileIDSelectionModel globalSelectionModel = FileIDSelectionModel.getInstance(); private static ContextMenu contextMenu; - /** - * displays the icon representing video files - */ + /** displays the icon representing video files */ @FXML - protected ImageView fileTypeImageView; + private ImageView fileTypeImageView; - /** - * displays the icon representing hash hits - */ + /** displays the icon representing hash hits */ @FXML - protected ImageView hashHitImageView; + private ImageView hashHitImageView; @FXML protected ImageView undisplayableImageView; - /** - * displays the icon representing follow up tag - */ + /** displays the icon representing follow up tag */ @FXML - protected ImageView followUpImageView; + private ImageView followUpImageView; @FXML - protected ToggleButton followUpToggle; - - /** - * the label that shows the name of the represented file - */ - @FXML - protected Label nameLabel; + private ToggleButton followUpToggle; @FXML - protected BorderPane imageBorder; + BorderPane imageBorder; + + /** the label that shows the name of the represented file */ + @FXML + Label nameLabel; @FXML protected ImageView imageView; @@ -156,13 +148,16 @@ public abstract class DrawableTileBase extends DrawableUIBase { case PRIMARY: if (t.getClickCount() == 1) { if (t.isControlDown()) { - globalSelectionModel.toggleSelection(fileID); } else { groupPane.makeSelection(t.isShiftDown(), fileID); } } else if (t.getClickCount() > 1) { - groupPane.activateSlideShowViewer(fileID); + if (groupPane.getGroupViewMode() == GroupViewMode.TILE) { + groupPane.activateSlideShowViewer(fileID); + } else { + groupPane.activateTileViewer(); + } } break; case SECONDARY: diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/GroupPane.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/GroupPane.java index 6e72f1c731..a3c66af62e 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/GroupPane.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/GroupPane.java @@ -198,9 +198,11 @@ public class GroupPane extends BorderPane { private Integer selectionAnchorIndex; - /** - * the current GroupViewMode of this GroupPane - */ + GroupViewMode getGroupViewMode() { + return groupViewMode.get(); + } + + /** the current GroupViewMode of this GroupPane */ private final SimpleObjectProperty groupViewMode = new SimpleObjectProperty<>(GroupViewMode.TILE); /** @@ -505,7 +507,6 @@ public class GroupPane extends BorderPane { if (groupViewMode.get() == GroupViewMode.SLIDE_SHOW) { slideShowPane.setFile(newFileId); } else { - scrollToFileID(newFileId); } }); diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/MetaDataPane.java b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/MetaDataPane.java index af618441d3..9461e15ab0 100644 --- a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/MetaDataPane.java +++ b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/gui/drawableviews/MetaDataPane.java @@ -1,7 +1,7 @@ /* * Autopsy Forensic Browser * - * Copyright 2013 Basis Technology Corp. + * Copyright 2013-15 Basis Technology Corp. * Contact: carrier sleuthkit org * * Licensed under the Apache License, Version 2.0 (the "License"); @@ -19,9 +19,9 @@ package org.sleuthkit.autopsy.imagegallery.gui.drawableviews; import com.google.common.eventbus.Subscribe; -import java.io.IOException; import java.util.Arrays; import java.util.Collection; +import java.util.List; import java.util.Objects; import java.util.Optional; import java.util.logging.Logger; @@ -29,9 +29,7 @@ import java.util.stream.Collectors; import javafx.application.Platform; import javafx.beans.property.SimpleObjectProperty; import javafx.beans.property.SimpleStringProperty; -import javafx.collections.ObservableList; import javafx.fxml.FXML; -import javafx.fxml.FXMLLoader; import javafx.scene.control.Label; import javafx.scene.control.TableCell; import javafx.scene.control.TableColumn; @@ -45,6 +43,7 @@ import org.apache.commons.lang3.StringUtils; import org.sleuthkit.autopsy.events.ContentTagAddedEvent; import org.sleuthkit.autopsy.events.ContentTagDeletedEvent; import org.sleuthkit.autopsy.events.TagEvent; +import org.sleuthkit.autopsy.imagegallery.FXMLConstructor; import org.sleuthkit.autopsy.imagegallery.ImageGalleryController; import org.sleuthkit.autopsy.imagegallery.datamodel.Category; import org.sleuthkit.autopsy.imagegallery.datamodel.CategoryManager; @@ -71,16 +70,7 @@ public class MetaDataPane extends DrawableUIBase { public MetaDataPane(ImageGalleryController controller) { super(controller); - - FXMLLoader fxmlLoader = new FXMLLoader(getClass().getResource("MetaDataPane.fxml")); - fxmlLoader.setRoot(this); - fxmlLoader.setController(this); - - try { - fxmlLoader.load(); - } catch (IOException exception) { - throw new RuntimeException(exception); - } + FXMLConstructor.construct(this, "MetaDataPane.fxml"); } @FXML @@ -167,7 +157,7 @@ public class MetaDataPane extends DrawableUIBase { public void updateUI() { getFile().ifPresent(file -> { - final ObservableList, ? extends Object>> attributesList = file.getAttributesList(); + final List, Collection>> attributesList = file.getAttributesList(); Platform.runLater(() -> { tableView.getItems().clear(); diff --git a/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/images/icon-hashtag.png b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/images/icon-hashtag.png new file mode 100644 index 0000000000..4fd9799874 Binary files /dev/null and b/ImageGallery/src/org/sleuthkit/autopsy/imagegallery/images/icon-hashtag.png differ diff --git a/branding/core/core.jar/org/netbeans/core/startup/Bundle.properties b/branding/core/core.jar/org/netbeans/core/startup/Bundle.properties index f1995d979d..7cdc53d7ae 100644 --- a/branding/core/core.jar/org/netbeans/core/startup/Bundle.properties +++ b/branding/core/core.jar/org/netbeans/core/startup/Bundle.properties @@ -1,5 +1,5 @@ #Updated by build script -#Mon, 27 Jul 2015 17:17:20 -0400 +#Tue, 28 Jul 2015 13:44:22 -0400 LBL_splash_window_title=Starting Autopsy SPLASH_HEIGHT=314 SPLASH_WIDTH=538 diff --git a/branding/modules/org-netbeans-core-windows.jar/org/netbeans/core/windows/view/ui/Bundle.properties b/branding/modules/org-netbeans-core-windows.jar/org/netbeans/core/windows/view/ui/Bundle.properties index 30447b5009..26b21e9fc3 100644 --- a/branding/modules/org-netbeans-core-windows.jar/org/netbeans/core/windows/view/ui/Bundle.properties +++ b/branding/modules/org-netbeans-core-windows.jar/org/netbeans/core/windows/view/ui/Bundle.properties @@ -1,5 +1,5 @@ #Updated by build script -#Mon, 27 Jul 2015 17:17:20 -0400 +#Tue, 28 Jul 2015 13:44:22 -0400 CTL_MainWindow_Title=Autopsy 3.1.3 CTL_MainWindow_Title_No_Project=Autopsy 3.1.3 diff --git a/docs/doxygen/modDevPython.dox b/docs/doxygen/modDevPython.dox index c8d7b36d63..6026a4b6ed 100755 --- a/docs/doxygen/modDevPython.dox +++ b/docs/doxygen/modDevPython.dox @@ -60,7 +60,8 @@ Jython will look in the module's folder to resolve these libraries. \subsection mod_dev_py_misc Minor Gotchas This section lists some helpful tips that we have found. These are all now in the sample modules, so refer to those for examples and a place to copy and paste from. - We haven't found a good way to debug while running inside of Autopsy. So, logging becomes critical. You need to go through a bunch of steps to get the logger to display your module name. See the sample module for a log() method that does all of this for you. -- When you name the file with your Python module in it, restrict its name to letters, numbers, and underscore (_). +- When you name the file with your Python module in it, restrict its name to letters, numbers, and underscore (_). +- Python modules using external libraries which load native code (SciPy, NumPy, etc.) are currently NOT supported. RuntimeError will be thrown. \section mod_dev_py_distribute Distribution To distribute and share your Python module, ZIP up the folder and send it around. Other users of the module should expand the ZIP file and drop the folder into their Autopsy Python folder.