Specify output parameters for ImageJ2 commands

@imagejan @stelfrich @jkh1
Is there somewhere an example for an IJ2 Command that not only contains the input parameters but also the output parameters? I guess, e.g., for automatically building KNIME nodes from IJ2 Commands also the output information must be provided?!

@NicoKiaru @ctrueden Could you maybe point me to an example?

Hi @Christian_Tischer,

I use plenty of these things. What you need to know is that if the output parameter has no way of being displayed, it’s being discarded. Unless you call the command programmatically. If you call it programmtically, you can get any outputs by doing:

Out out0 = (Out) (command.run(MyCommand.class, true, "input0", in).get().getOutput("out0"));

If you want to display it using an UI, you can have a look at this discussion:




Ok! Looks easy enough, basically, that’s it?

@Parameter(type = ItemIO.OUTPUT)

Then, related to that, I think @haesleinhuepf showed once how to programmatically find out the input and output parameters of given a Command. I think it was something like below:

SomeSortOfInputsMap = getInputs( SomeCommand.class ); 
SomeSortOfOutputsMap = getOutputs( SomeCommand.class );

Is there some mechanism like this?

Noooow I know why you mention me repeatedly with @-Parameter-related questions: You mix me up with the other dreadlock guy :wink: Sorry, but I hardly work with @-Parameters these days

1 Like

Somehow I thought it was you, really :wink:
Anyway @maarzt, could you help here?
@haesleinhuepf, if you run into him, could you point him here? :slight_smile:

1 Like

Your first place to go for examples is the ImageJ Tutorials.

$ git grep OUTPUT
maven-projects/add-two-datasets/src/main/java/AddTwoDatasets.java:      @Parameter(label = "Result 1", type = ItemIO.OUTPUT)
maven-projects/add-two-datasets/src/main/java/AddTwoDatasets.java:      @Parameter(label = "Result 2", type = ItemIO.OUTPUT)
maven-projects/add-two-datasets/src/main/java/AddTwoDatasets.java:      @Parameter(label = "Result 3", type = ItemIO.OUTPUT)
maven-projects/create-a-new-op/src/main/java/CreateANewOp.java:         @Parameter(type = ItemIO.OUTPUT)
maven-projects/create-a-new-op/src/main/java/Ramp.java: @Parameter(type = ItemIO.OUTPUT)
maven-projects/create-a-new-op/src/main/java/RandomBlobs.java:  @Parameter(type = ItemIO.OUTPUT)
maven-projects/low-pass-filter/src/main/java/LowPassFilter.java:        @Parameter(type = ItemIO.OUTPUT)
maven-projects/metadata/src/main/java/GetMetadata.java:    @Parameter(label = "Metadata", type = ItemIO.OUTPUT)
maven-projects/simple-commands/src/main/java/GradientImage.java:        @Parameter(type = ItemIO.OUTPUT)
maven-projects/simple-commands/src/main/java/GradientImage.java:                // NB: Because the dataset is declared as an "OUTPUT" above,
maven-projects/simple-commands/src/main/java/HelloWorld.java: * {@code @Parameter(type = ItemIO.OUTPUT)} annotation.
maven-projects/simple-commands/src/main/java/HelloWorld.java:   @Parameter(type = ItemIO.OUTPUT)
maven-projects/simple-commands/src/main/java/OpenImage.java:    @Parameter(type = ItemIO.OUTPUT)
maven-projects/swing-example/src/main/java/DeconvolutionCommand.java:   @Parameter(type = ItemIO.OUTPUT)
maven-projects/swing-example/src/main/java/DeconvolutionCommandSwing.java:      @Parameter(type = ItemIO.OUTPUT)
maven-projects/using-ops/src/main/java/UsingOpsDog.java:    @Parameter(type = ItemIO.OUTPUT)
maven-projects/widget-demo/src/main/java/WidgetDemo.java:       // ItemIO.OUTPUT rather than the usual ItemIO.INPUT. Output parameter
maven-projects/widget-demo/src/main/java/WidgetDemo.java:       @Parameter(label = "Results", type = ItemIO.OUTPUT)

Edit: Ah, I guess that example does not yet show how to harvest the outputs. The run() method returns a Future<Module>. Call get() on it to block until execution is complete, and receive the Module. Call getOutputs() on the Module to receive a map of the output key/value pairs.


@ctrueden thank you very much for the answer!
As I told you already in an e-mail once, we are interested in automatically generating binary code from SciJava Commands such that they could be run “in the cloud”.
I guess one would also need for this a PostProcessor that writes all the module outputs to disk, such that they can be read by the next processing modules.

  1. Does such a WriteOutputsToDiskPostprocessor exist already?
  2. How does all of this relate to ImageJ-Server? Is ImageJ-Server in fact already doing some of the automated wrapping of Commands into something that can be called from non-Java applications?

@Christian_Tischer in addition to the tutorials and examples above, you can also have a look at these ImageJ2 command plugins:

They all define some outputs and have a headless=true annotation, so they get auto-rendered as #knime nodes by the KNIME ImageJ integration.

Regarding PostprocessorPlugins, here are some source code links for your inspiration:


No, I have not seen any implementation of that. Decisions would need to be made regarding how to serialize/externalize/marshal each object.

To an extent, yes; see the imagej-server API documentation. You could e.g. use this to query and invoke modules from other languages such as JavaScript. However, code would still need to be written to harvest and persist the outputs after execution—the ImageJ Server does not do this itself.

Please note that the ImageJ Server is not under active development at the moment due to lack of resources, and needs some work to reduce security risks associated with using it. See:

1 Like

Yes, yes it’s possible to use the CommandService and CommandInfo:

CommandService commandService = ...;
List<CommandInfo> commandInfos = commandService.getCommandsOfType(Command.class);
CommandInfo commandInfo = commandInfos.get(0);
Iterable<ModuleItem<?>> inputs = commandInfo.inputs();
Iterable<ModuleItem<?>> outputs = commandInfo.outputs();	

Hi @imagejan @ctrueden

I think at some point there was an idea that such image inputs would be automatically treated as files when the context is a headless call from the command line:

Do you know whether this still is on someone’s agenda?

To me, this is interesting, because in order to also make Commands also runnable from the command line I recently mostly used a File inputImage parameter rather than an Img. Also for batching the Commands having a File seemed useful. Is this the recommended way of doing things or could one also use an Img?

For batch processing with the SciJava batch processor, using Img parameters is supported. I.e. you can use a Dataset (or anything that a Dataset can be converted to, such as Img) parameter:

  • in a script:

    #@ Img input
  • in Java:

    private Img input;

… and it will automatically be populated from a list of files when running in batch.

For those interested in the source code, it is the DatasetBatchInputProvider (in combination with any converters registered with the ConvertService) that takes care of this:

For single usage of Dataset parameters to be populated from Files (when run headless, or when no image is open in the GUI) this was first discussed here:

… and is now being tracked here:

I currently don’t have resources to work on this, but would be happy to review pull requests or provide my opinion or some help :slightly_smiling_face: