Recommendations for Creating a Writer Plugin in ImageJ1 and 2

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
6 messages Options
Reply | Threaded
Open this post in threaded view
|

Recommendations for Creating a Writer Plugin in ImageJ1 and 2

Alan Brooks
I am looking for some recommendations. I have been asked to create a file writer plugin for ImageJ that can write a proprietary raw data image file format. (This is not because we think this format is good--it is not--but it is for customer that wants to manipulate intermediate data and then run it through the rest of our software system.)

Our company's service personnel use ImageJ in many locations without internet access and currently have ImageJ1 (varied versions) deployed on our machines. No one yet uses ImageJ2 (or Fiji) but I want to consider my options.

Ideally, I'd like to write something that works well as an ImageJ1 writer plugin but also could be used as an ImageJ2 writer (and reader). I already have a crufty ImageJ1 reader for this format that I don't plan on touching much at this time unless there are enhancements that come for little cost/time.

As far as I can tell, the recommended method of creating an ImageJ1 writer is to make a PluginFilter that writes the file and then put it in a jar with a plugins.config file with contents such as:
   File>Save As, "Format Name...", Format_Writer

From what I read on forums ([1],[2]) and on https://github.com/scifio/scifio/wiki/Adding-support-for-an-image-format, the recommended method of creating an ImageJ2 file reader or writer plugin is to make a SCIFIO plugin that implements AbstractFormat and put the resulting jar somewhere where it is automatically found by ImageJ2 (I'm not sure where that is -- perhaps just the ).

[1]: http://imagej.1557.x6.nabble.com/Handle-Extra-Files-Types-not-working-td5008224.html#a5008244
[2]: http://imagej.1557.x6.nabble.com/Fiji-the-nrrd-file-format-and-HandleExtraFileTypes-td5002602.html#a5002724

Specific Questions:
1. Is it unreasonable to share writer/reader code between ImageJ1 and ImageJ2?
2. Where do I put writer/reader jars for ImageJ2? Just in the normal /jars folder?

Thanks,
Alan
Reply | Threaded
Open this post in threaded view
|

Re: Recommendations for Creating a Writer Plugin in ImageJ1 and 2

dscho
Hi Alan,

On Tue, 1 Jul 2014, alanb wrote:

> I am looking for some recommendations. I have been asked to create a
> file writer plugin for ImageJ that can write a proprietary raw data
> image file format. (This is not because we think this format is good--it
> is not--but it is for customer that wants to manipulate intermediate
> data and then run it through the rest of our software system.)
>
> Our company's service personnel use ImageJ in many locations without
> internet access and currently have ImageJ1 (varied versions) deployed on
> our machines. No one yet uses ImageJ2 (or Fiji) but I want to consider
> my options.
>
> Ideally, I'd like to write something that works well as an ImageJ1
> writer plugin but also could be used as an ImageJ2 writer (and reader).
> I already have a crufty ImageJ1 reader for this format that I don't plan
> on touching much at this time unless there are enhancements that come
> for little cost/time.
>
> As far as I can tell, the recommended method of creating an ImageJ1
> writer is to make a PluginFilter that writes the file and then put it in
> a jar with a plugins.config file with contents such as:
>    File>Save As, "Format Name...", Format_Writer

Correct, maybe two more suggestions:

- the PlugInFilter (careful about the upper-case "i") takes an ImagePlus
  and a String in its setup() method, but only an ImageProcessor in the
  run() method. If you want to support writing stacks, you definitely want
  to store the ImagePlus in a field and not use the ImageProcessor (which
  is *just* the current slice). Also, do not return DOES_STACKS in that
  case: that will trigger the run() method to be called *for every* slice.

- ImageJ 1.x supports macros by reusing the label of the menu item for the
  run() call. That means that no two menu items, no matter whether they
  live in the same menu or not, can share the same label. Since it is
  common to desire the same name for reader and writer, the convention is
  to append a single space for the writer. It is a bit clumsy, but that's
  how things work.

> From what I read on forums ([1],[2]) and on
> https://github.com/scifio/scifio/wiki/Adding-support-for-an-image-format,
> the recommended method of creating an ImageJ2 file reader or writer plugin
> is to make a SCIFIO plugin that implements AbstractFormat and put the
> resulting jar somewhere where it is automatically found by ImageJ2 (I'm not
> sure where that is -- perhaps just the ).

Exactly: you just have to put the .jar file onto the class path. The
convention is to put plugins into the plugins/ directory, but even jars/
will work.

The details why this works are quite cunning, if I may say so: we are
using a quite powerful framework based on annotation processing. That
means that the annotations (these funky "@Plugin(type = Format.class)"
thingies) are not only attached to the class definition, but can be
inspected *at compile time*, by a so-called annotation processor. One such
annotation processor indexes the just-compiled annotations and writes out
the index into META-INF/ which is included in the .jar file.

The bottom line for the developer is that they do not need to conform to
some file name convention, do not need to put the files into the exact
right spot, do not need a plugins.config file. The .jar file just needs to
be on the class path and that's it.

There is another, quite important benefit to this framework: new plugin
types can be defined very easily. Just define an interface that extends
the (empty) SciJavaPlugin interface. That's it. All plugins need to do is
to implement that interface and annotate the class with @Plugin(type =
MyCoolNewPlugin.class). To consume those plugins, one needs only ask the
PluginService associated with the current Context. But I digress... and I
should find the time to write a blog post about this.

> Specific Questions:
> 1. Is it unreasonable to share writer/reader code between ImageJ1 and
> ImageJ2?

It makes a ton of sense, if you ask me. In particular, I would try to
avoid conflating the logic to write the image with the specifics of the
plugins as much as possible.

> 2. Where do I put writer/reader jars for ImageJ2? Just in the normal
> /jars folder?

Well, I would put it into the plugins/ directory.

The jars/ directory was only introduced by Fiji (and not really picked up
by ImageJ 1.x until much much later) to avoid problems with the naming
conventions: in the early days, we shipped the jai_core.jar file as
downloaded from the website. You will note the underscore which ImageJ 1.x
mistook as an indicator that this .jar file is a plugin. Worse: the
absence of a plugins.config file was taken to suggest that the contents of
the .jar file should be inspected for .class files having an underscore in
their file name, and sure enough, there was one. Actually, four. They were
faithfully added into the Plugins>com>sun>media>jai>rmi menu.
Unfortunately, we could not come up with a better solution than to add
*another* directory.

Traditionally, the only reason to have a hard-coded directory for the
plugins is to be able to throw away the class loader that loaded the
plugin classes and make a new one (because class loaders cannot unload
classes by default), i.e. the architecture was influenced by an
implementation detail.

So in the future, I'd really rather have the plugins anywhere in the class
path, for tradition's sake probably in plugins/.

Ciao,
Dscho

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: Recommendations for Creating a Writer Plugin in ImageJ1 and 2

Rasband, Wayne (NIH/NIMH) [E]
In reply to this post by Alan Brooks
On Jul 1, 2014, at 4:04 PM, alanb wrote:

> I am looking for some recommendations. I have been asked to create a file
> writer plugin for ImageJ that can write a proprietary raw data image file
> format. (This is not because we think this format is good--it is not--but it
> is for customer that wants to manipulate intermediate data and then run it
> through the rest of our software system.)
>
> Our company's service personnel use ImageJ in many locations without
> internet access and currently have ImageJ1 (varied versions) deployed on our
> machines. No one yet uses ImageJ2 (or Fiji) but I want to consider my
> options.
>
> Ideally, I'd like to write something that works well as an ImageJ1 writer
> plugin but also could be used as an ImageJ2 writer (and reader). I already
> have a crufty ImageJ1 reader for this format that I don't plan on touching
> much at this time unless there are enhancements that come for little
> cost/time.
>
> As far as I can tell, the recommended method of creating an ImageJ1 writer
> is to make a PluginFilter that writes the file and then put it in a jar with
> a plugins.config file with contents such as:
>   File>Save As, "Format Name...", Format_Writer

I would make the writer a PlugIn, which is simpler and easier to understand. For an example, look at the PNM_Writer plugin (http://imagej.nih.gov/ij/source/ij/plugin/PNM_Writer.java), which implements the File>Save As>PGM command.

-wayne

> From what I read on forums ([1],[2]) and on
> https://github.com/scifio/scifio/wiki/Adding-support-for-an-image-format,
> the recommended method of creating an ImageJ2 file reader or writer plugin
> is to make a SCIFIO plugin that implements AbstractFormat and put the
> resulting jar somewhere where it is automatically found by ImageJ2 (I'm not
> sure where that is -- perhaps just the ).
>
> [1]:
> http://imagej.1557.x6.nabble.com/Handle-Extra-Files-Types-not-working-td5008224.html#a5008244
> [2]:
> http://imagej.1557.x6.nabble.com/Fiji-the-nrrd-file-format-and-HandleExtraFileTypes-td5002602.html#a5002724
>
> Specific Questions:
> 1. Is it unreasonable to share writer/reader code between ImageJ1 and
> ImageJ2?
> 2. Where do I put writer/reader jars for ImageJ2? Just in the normal /jars
> folder?
>
> Thanks,
> Alan
>
>
>
> --
> View this message in context: http://imagej.1557.x6.nabble.com/Recommendations-for-Creating-a-Writer-Plugin-in-ImageJ1-and-2-tp5008522.html
> Sent from the ImageJ mailing list archive at Nabble.com.
>
> --
> ImageJ mailing list: http://imagej.nih.gov/ij/list.html

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: Recommendations for Creating a Writer Plugin in ImageJ1 and 2

Alan Brooks
Dscho & Wayne,

Thanks for the feedback. I'd be interested in reading that blog post about
adding new plugin types, Dscho, so here's my vote to encourage you to write
it.

Thanks for the details on the plugins/jars folders. If you can't tell, I've
been an ImageJ1 user for a while, but am just now becoming familiar with
the Fiji and ImageJ2 community.


> In particular, I would try to avoid conflating the logic to write the
> image with the specifics of the plugins as much as possible.

My plan is to make a general class that knows how to serialize,
deserialize, display info about, and test the file format reader/writer.
This could be used in any Java program and not tied to ImageJ1 or 2. Then,
I will write the plugins (one for IJ1, one for SCIFIO) as a user of that
class.

I would make the writer a PlugIn, which is simpler and easier to
> understand. For an example, look at the PNM_Writer plugin (
> http://imagej.nih.gov/ij/source/ij/plugin/PNM_Writer.java), which
> implements the File>Save As>PGM command.
>
I agree that PlugInFilter isn't doing anything that useful for a file
writer. Thanks for the reference.

Cheers,
Alan

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: Recommendations for Creating a Writer Plugin in ImageJ1 and 2

dscho
Hi Alan,

On Wed, 2 Jul 2014, Alan Brooks wrote:

> Thanks for the feedback. I'd be interested in reading that blog post
> about adding new plugin types, Dscho, so here's my vote to encourage you
> to write it.

Thanks for the encouragement, but at the moment I seriously need time more
than anything else...

> Thanks for the details on the plugins/jars folders. If you can't tell,
> I've been an ImageJ1 user for a while, but am just now becoming familiar
> with the Fiji and ImageJ2 community.

Well, to be honest, I do not see three different communities. It is
unfortunate that Fiji is often perceived as something different from
ImageJ; all I intended it to be is a distribution of ImageJ with a couple
of plugins. And ImageJ2 is the logical next step: preparing ImageJ for the
future challenges of scientific image processing.

> > In particular, I would try to avoid conflating the logic to write the
> > image with the specifics of the plugins as much as possible.
>
> My plan is to make a general class that knows how to serialize,
> deserialize, display info about, and test the file format reader/writer.
> This could be used in any Java program and not tied to ImageJ1 or 2.
> Then, I will write the plugins (one for IJ1, one for SCIFIO) as a user
> of that class.

That sounds like a very good plan to me!

> > I would make the writer a PlugIn, which is simpler and easier to
> > understand. For an example, look at the PNM_Writer plugin (
> > http://imagej.nih.gov/ij/source/ij/plugin/PNM_Writer.java), which
> > implements the File>Save As>PGM command.
>
> I agree that PlugInFilter isn't doing anything that useful for a file
> writer. Thanks for the reference.

Actually, the only reason you would want a PlugInFilter is to avoid having
to reimplement the test whether there is a matching current image. And
this is not the only thing you will have to reimplement, just like every
other Writer plugin...

I guess maximal freedom comes at maximum price... ;-)

Ciao,
Dscho

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html
Reply | Threaded
Open this post in threaded view
|

Re: Recommendations for Creating a Writer Plugin in ImageJ1 and 2

ctrueden
Hi Alan,

> Our company's service personnel use ImageJ in many locations without
> internet access and currently have ImageJ1 (varied versions) deployed
> on our machines. No one yet uses ImageJ2 (or Fiji) but I want to
> consider my options.
>
> Ideally, I'd like to write something that works well as an ImageJ1
> writer plugin but also could be used as an ImageJ2 writer (and
> reader).
...
> My plan is to make a general class that knows how to serialize,
> deserialize, display info about, and test the file format
> reader/writer. This could be used in any Java program and not tied
> to ImageJ1 or 2. Then, I will write the plugins (one for IJ1, one
> for SCIFIO) as a user of that class.

From your description, it sounds like you are not sure whether your company
will use ImageJ2 in the near future. If you must stay with vanilla ImageJ1,
and you only need to support your file format internally, then I would
suggest creating only a pure ImageJ1 plugin, integrate it with
HandleExtraFileTypes and skip the SCIFIO format plugin. This solution also
works in ImageJ2, with or without the SCIFIO option enabled: ultimately, if
nothing else can read the file format then the opener logic falls back to
IJ1 which falls back on HandleExtraFileTypes.

However, if you are able to use ImageJ2, and/or if you plan to release the
file format plugin to an audience beyond your company's internal service
personnel, then my advice would be to focus on creating a SCIFIO Format
plugin and forget the ImageJ1 plugin. The SCIFIO library is not an
ImageJ-specific project -- it was created precisely to eliminate the need
to implement multiple file format readers or adapters for different
systems. All SCIFIO formats already integrate with several software
packages "for free" including ImageJ (File > Open as well as File > Import
> Image...), KNIME, CellProfiler and others.

Either way, there should be no need to create both an ImageJ1 plugin and a
SCIFIO format.

Regards,
Curtis


On Wed, Jul 2, 2014 at 6:42 PM, Johannes Schindelin <
[hidden email]> wrote:

> Hi Alan,
>
> On Wed, 2 Jul 2014, Alan Brooks wrote:
>
> > Thanks for the feedback. I'd be interested in reading that blog post
> > about adding new plugin types, Dscho, so here's my vote to encourage you
> > to write it.
>
> Thanks for the encouragement, but at the moment I seriously need time more
> than anything else...
>
> > Thanks for the details on the plugins/jars folders. If you can't tell,
> > I've been an ImageJ1 user for a while, but am just now becoming familiar
> > with the Fiji and ImageJ2 community.
>
> Well, to be honest, I do not see three different communities. It is
> unfortunate that Fiji is often perceived as something different from
> ImageJ; all I intended it to be is a distribution of ImageJ with a couple
> of plugins. And ImageJ2 is the logical next step: preparing ImageJ for the
> future challenges of scientific image processing.
>
> > > In particular, I would try to avoid conflating the logic to write the
> > > image with the specifics of the plugins as much as possible.
> >
> > My plan is to make a general class that knows how to serialize,
> > deserialize, display info about, and test the file format reader/writer.
> > This could be used in any Java program and not tied to ImageJ1 or 2.
> > Then, I will write the plugins (one for IJ1, one for SCIFIO) as a user
> > of that class.
>
> That sounds like a very good plan to me!
>
> > > I would make the writer a PlugIn, which is simpler and easier to
> > > understand. For an example, look at the PNM_Writer plugin (
> > > http://imagej.nih.gov/ij/source/ij/plugin/PNM_Writer.java), which
> > > implements the File>Save As>PGM command.
> >
> > I agree that PlugInFilter isn't doing anything that useful for a file
> > writer. Thanks for the reference.
>
> Actually, the only reason you would want a PlugInFilter is to avoid having
> to reimplement the test whether there is a matching current image. And
> this is not the only thing you will have to reimplement, just like every
> other Writer plugin...
>
> I guess maximal freedom comes at maximum price... ;-)
>
> Ciao,
> Dscho
>
> --
> ImageJ mailing list: http://imagej.nih.gov/ij/list.html
>

--
ImageJ mailing list: http://imagej.nih.gov/ij/list.html