Galatee is a Java library for exploring and searching in large image collection where images are annotated.
The library is mainly developped for browsing-searching image collections and annotating images.
Feel free to send me an email at nicolas.james@gmail.com if you are interested by this library.
The Galatee library provides:
visualization of a list of images (with associated metadata): images are referenced by a
URI object. Schemes of the
URI can be
file for a local image file, or
http for an image file accessible via
HTTP,
textual search in the image list (based on the value of the image
URI and on the image description) using a Lucene in-memory index,
downloading, in-memory loading and resizing of an image is made only when it's necessary (something like a load when you see),
multi-threading for the downloading, loading, resizing of the images,
configuration via a Galatee.properties file:
customize the item visualization (image size, text area size),
cache directory for downloaded files.
implementing its own item visualization is easy (just a class to extend, the GCellPanel class).
Galatee has an EventListener interface for easily forwarding the user interaction to your code:
public interface GListener extends EventListener {
public void itemDoubleClicked(GEvent e);
public void selectionChanged(GEvent e);
}
package net.trevize.galatee.main;
import java.awt.BorderLayout;
import javax.swing.JFrame;
import javax.swing.JPanel;
import net.trevize.galatee.GEvent;
import net.trevize.galatee.GListener;
import net.trevize.galatee.Galatee;
import net.trevize.galatee.GalateeFactory;
import net.trevize.tinker.SystemCommandHandler2;
/**
*
*
* @author Nicolas James <nicolas.james@gmail.com> [[http://njames.trevize.net]]
* DirectoryExplorer.java - Jan 29, 2010
*/
public class DirectoryExplorer {
private String path;
public DirectoryExplorer(String path) {
this.path = path;
init();
}
private void init() {
System.out.println("*** DirectoryExplorer with Galatee main test ***");
System.out.println("initializing...");
int n = 3; //initial number of columns.
System.out.println("path=[" + path + "]");
System.out.println("display in " + n + " columns");
//using the GalateeFactory for getting a Galatee object.
Galatee g = GalateeFactory.loadDatasetFromDirectory(path, false);
JFrame f = new JFrame("*** Galatee main test ***");
JPanel p = new JPanel();
p.setLayout(new BorderLayout());
f.getContentPane().add(p);
p.add(g);
//implementing a GListener for handling events of the Galatee components.
GListener listener = new GListener() {
class SystemCommandThread extends Thread {
private SystemCommandHandler2 sch2 = new SystemCommandHandler2();
private String command;
public SystemCommandThread(String command) {
this.command = command;
}
public void run() {
String[] commands = new String[1];
commands[0] = command;
sch2.exec(commands);
}
}
//if double click we use ImageMagick "display" command to display the image.
@Override
public void itemDoubleClicked(GEvent e) {
System.out.println("item doubleclicked ["
+ e.getSelectedItem().getLocalFilepath() + "]");
SystemCommandThread sct = new SystemCommandThread("display \""
+ e.getSelectedItem().getLocalFilepath() + "\"");
sct.start();
}
@Override
public void selectionChanged(GEvent e) {
System.out.println("changing selection for ["
+ e.getSelectedItem().getLocalFilepath() + "]");
}
};
g.addGalateeListener(listener);
g.enableSearchFunctionality();
System.out.println("initialization ended.");
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.setSize(512, 512);
f.setLocationRelativeTo(null);
f.setVisible(true);
}
public static void main(String args[]) {
String path = "/home/nicolas/datasets/PascalVOC/voc2006/voc2006_trainval/VOCdevkit/VOC2006/PNGImages";
DirectoryExplorer explorer = new DirectoryExplorer(path);
}
}
The library is designed and programmed on a GNU/Linux platform but it should work also on the MS-Windows platform (if not, drop me a line at nicolas.james@gmail.com about any problem you encounter).
However, some of the embedded features of the library use external applications (e.g. those of the ImageMagick project) on a GNU/Linux system through a special class called SystemCommandHandler2 which is only available for GNU/Linux system, so some functionnalities are only available on GNU/Linux and Unix systems.
Galatee use the following libraries:
commons-vfs, commons-codec, commons-httpclient, commons-io, commons-lang, log4j, lucene-core: under Apache license
-
some of my libraries: Tinker, Jmagine: under GPLv2 license
conja
JAI: Java Research License (JRL)
Galatee, a Java library for exploring image collection in Java.
Copyright © 2009-2010, Nicolas James.
http://njames.trevize.net/wiki/projects:galatee
Galatee is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version.
Galatee is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public License along with this Module; if not, write to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
Galatee used in the LabelMeBrowser, an application for mining the LabelMe image collection. | Galatee in the IIDFFileBrowser, an application for exploring image collection modelized with the IIDF (Image Index and Data File) image collection model. |
Galatee with TRECVID2005. | |
surprising: It appears some images that contains problems (wrong
JPEG header etc.) cannot been open by JAI but can be using ImageIO.read(…).
BUG: when right click for displaying the contextual menu of an item, the JTable component automatically scrolls the panel, this produce a bug with the ItemChanged event. This changes nothing for the user, but an exception is thrown.
make an update to the GItem class, notably the GItem.getLocalFilepath() method (GItem.getLocalFilepath(boolean standard_access_required)), for generalized the access to the files (when browsing a TAR, we don't want to unpack the tar, but when we want to work on an image GItem.getLocalFilepath(true) unpack the image and update the localfilepath).
feature request: open tar files that contains a dataset (as in ImageNet). It could be performed with Apache common VFS, and the archives has not to be decompressed, but commons VFS seems not supporting parallel access to one tar (even in read only). I have try using java stream pipes (PipeInputStream and PipeOutputSteam) and it could really works… I have to handle the access to the tar with locks…
When loading very large image databases (I've tested with 67k documents, a snapshot of the
ESP Game data), it seems JAI has memory issues:
Error: One factory fails for the operation "stream"
Occurs in: javax.media.jai.ThreadSafeOperationRegistry
This bug occurs with the pure Java mode, and with the JAI accelerator. It's not a critical bug because we don't open such a large database usually.
the last loaded image is not displayed in the GUI if it is the current edited cell (i.e. the currently selected image) it's cause of the _TableCellEditor, cp.setimage(null) and the image is loaded after that, so if the selection hasn't change, the cp.setImage(image) have not been done… resolved in v0.43
be careful: the SystemCommandHandler for using the imagemagick display command is buggy. resolve in v0.43. In fact, the SystemCommandHandler using naively the Process class in Java is complicated to use, so I've integrated my SystemCommandHandler2 using a character stream in the input of a Unix Shell. Obviously, this trick only run under GNU/Linux, for Windows the SystemCommandHandler is still in the project.
si le nombre de document n'est pas divisible par le nombre de ligne il y a des cellules vide, normalement une cellule vide n'est pas affichée, mais lorsque le texte de la description est plus grand que la hauteur de l'image une cellule vide est rendue. Unreproducible.
concernant le thread de chargement des images, il serait judicieux de coder un pool de thread pour améliorer le chargement des images, et utiliser un ExecutorService plutôt qu'un pool codé “old school” avec des blocs synchronized. resolved in v0.43.
when the display is parametrized with 3 columns, but there are only two results, typing '-' for removing a column is not performed in the GUI (from the user eyes), because the number of column is 3. The problem is here too with the key '+, 'add a column' action then shouldn't add a column if no data to put in it. resolved in v0.43.
v0.45 → v0.46
lucene in_memory index for searching
bug correction: edited cell not immediatly displayed when browsing and specially when searching. corrected.
bug correction: scrolling to an item is not ensure that this item is in the visible rectangle of the JTable. corrected.
v0.42 → v0.43
the key '-' was not correctly mapped (the action for removing a column in the browser), it's corrected.
Conja is now used for the loading of the image queue (using an implementation of Iterable, GItemList and an implementation of Iterator, GItemListIterator).
the first object of the data associated to a GItem, is the description displayed in the browser, the other objects are that you want.
the key page_up and page_down was very buggy and changed the current selection. For now, the scrolling is ok, and going page_up and page_down do not modify the current selection.
the verification that a cell was not empty when moving with arrow keys was not made, and an Exception was thrown. Resolved.
the imageDescriptionSpacer in the GCellPanel was added even if the imageDescriptionWidth == 0 (no description).
An editor has been added to the project: _TableCellEditor. It's basically an example, could be completly rewritten, for now it just allows to copy the filepath to the clipboard.
introduction of a Galatee.properties and a GalateeProperties class for storing all the configuration of Galatee.
from now Galatee take in argument a list of
URI (no more a list of File object), this allows to have image located on the web. If the scheme of the
URI is “http” the image is downloaded in a temporary directory (see GalateeProperties), if the scheme is “file” nothing is changed compared to previously when Galatee took in argument a list of File object.
introduction of HTTPAbsoluteFileListDatasetExplorer class, which take in argument a text file containing at each line a relative
URL. I use the term of “relative
URL” because each line will be prefixed by a “host_prefix” to build a valid
URL.
A use case of such a class is a web directory, whatever is the server hosting your files, you just need (1) a text file that contains the relative path to your images, (2) the
URL prefix, i.e. the web adress of the server that contains your image dataset.