This notebook covers how to use ImageJ as a library from Python. A major advantage of this approach is the ability to combine ImageJ with other tools available from the Python software ecosystem, including NumPy, SciPy, scikit-image, CellProfiler, OpenCV, ITK and more.
This notebook assumes familiarity with the ImageJ API. Detailed tutorials in that regard can be found in the other notebooks.
PyImageJ supports running ImageJ macros, scripts and plugins. Checkout the examples below to see how each function works. First let's initialize ImageJ with Fiji so we can use some plugins.
import imagej
# initialize imagej
ij = imagej.init('sc.fiji:fiji')
print(f"ImageJ version: {ij.getVersion()}")
11:32:21.848 [SciJava-49b0d71e-Thread-0] DEBUG loci.formats.ClassList - Could not find loci.formats.in.URLReader java.lang.ClassNotFoundException: loci.formats.in.URLReader at java.net.URLClassLoader.findClass(URLClassLoader.java:382) at java.lang.ClassLoader.loadClass(ClassLoader.java:419) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:352) at java.lang.ClassLoader.loadClass(ClassLoader.java:352) at java.lang.Class.forName0(Native Method) at java.lang.Class.forName(Class.java:264) at loci.formats.ClassList.parseLine(ClassList.java:196) at loci.formats.ClassList.parseFile(ClassList.java:258) at loci.formats.ClassList.<init>(ClassList.java:138) at loci.formats.ClassList.<init>(ClassList.java:122) at loci.formats.ImageReader.getDefaultReaderClasses(ImageReader.java:80) at io.scif.bf.BioFormatsFormat.cacheReaderClasses(BioFormatsFormat.java:538) at io.scif.bf.BioFormatsFormat.<init>(BioFormatsFormat.java:139) at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) at java.lang.reflect.Constructor.newInstance(Constructor.java:423) at java.lang.Class.newInstance(Class.java:442) at org.scijava.plugin.PluginInfo.createInstance(PluginInfo.java:304) at org.scijava.plugin.DefaultPluginService.createInstance(DefaultPluginService.java:234) at org.scijava.plugin.DefaultPluginService.createInstances(DefaultPluginService.java:223) at org.scijava.plugin.DefaultPluginService.createInstancesOfType(DefaultPluginService.java:214) at io.scif.services.DefaultFormatService.lambda$initialize$0(DefaultFormatService.java:459) at org.scijava.thread.DefaultThreadService.lambda$wrap$1(DefaultThreadService.java:211) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run(FutureTask.java:266) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:32:21.859 [SciJava-49b0d71e-Thread-0] DEBUG loci.formats.ClassList - Could not find loci.formats.in.SlideBook6Reader java.lang.ClassNotFoundException: loci.formats.in.SlideBook6Reader at java.net.URLClassLoader.findClass(URLClassLoader.java:382) at java.lang.ClassLoader.loadClass(ClassLoader.java:419) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:352) at java.lang.ClassLoader.loadClass(ClassLoader.java:352) at java.lang.Class.forName0(Native Method) at java.lang.Class.forName(Class.java:264) at loci.formats.ClassList.parseLine(ClassList.java:196) at loci.formats.ClassList.parseFile(ClassList.java:258) at loci.formats.ClassList.<init>(ClassList.java:138) at loci.formats.ClassList.<init>(ClassList.java:122) at loci.formats.ImageReader.getDefaultReaderClasses(ImageReader.java:80) at io.scif.bf.BioFormatsFormat.cacheReaderClasses(BioFormatsFormat.java:538) at io.scif.bf.BioFormatsFormat.<init>(BioFormatsFormat.java:139) at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) at java.lang.reflect.Constructor.newInstance(Constructor.java:423) at java.lang.Class.newInstance(Class.java:442) at org.scijava.plugin.PluginInfo.createInstance(PluginInfo.java:304) at org.scijava.plugin.DefaultPluginService.createInstance(DefaultPluginService.java:234) at org.scijava.plugin.DefaultPluginService.createInstances(DefaultPluginService.java:223) at org.scijava.plugin.DefaultPluginService.createInstancesOfType(DefaultPluginService.java:214) at io.scif.services.DefaultFormatService.lambda$initialize$0(DefaultFormatService.java:459) at org.scijava.thread.DefaultThreadService.lambda$wrap$1(DefaultThreadService.java:211) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run(FutureTask.java:266) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:32:21.860 [SciJava-49b0d71e-Thread-0] DEBUG loci.formats.ClassList - Could not find loci.formats.in.ScreenReader java.lang.ClassNotFoundException: loci.formats.in.ScreenReader at java.net.URLClassLoader.findClass(URLClassLoader.java:382) at java.lang.ClassLoader.loadClass(ClassLoader.java:419) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:352) at java.lang.ClassLoader.loadClass(ClassLoader.java:352) at java.lang.Class.forName0(Native Method) at java.lang.Class.forName(Class.java:264) at loci.formats.ClassList.parseLine(ClassList.java:196) at loci.formats.ClassList.parseFile(ClassList.java:258) at loci.formats.ClassList.<init>(ClassList.java:138) at loci.formats.ClassList.<init>(ClassList.java:122) at loci.formats.ImageReader.getDefaultReaderClasses(ImageReader.java:80) at io.scif.bf.BioFormatsFormat.cacheReaderClasses(BioFormatsFormat.java:538) at io.scif.bf.BioFormatsFormat.<init>(BioFormatsFormat.java:139) at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) at java.lang.reflect.Constructor.newInstance(Constructor.java:423) at java.lang.Class.newInstance(Class.java:442) at org.scijava.plugin.PluginInfo.createInstance(PluginInfo.java:304) at org.scijava.plugin.DefaultPluginService.createInstance(DefaultPluginService.java:234) at org.scijava.plugin.DefaultPluginService.createInstances(DefaultPluginService.java:223) at org.scijava.plugin.DefaultPluginService.createInstancesOfType(DefaultPluginService.java:214) at io.scif.services.DefaultFormatService.lambda$initialize$0(DefaultFormatService.java:459) at org.scijava.thread.DefaultThreadService.lambda$wrap$1(DefaultThreadService.java:211) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run(FutureTask.java:266) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) 11:32:21.861 [SciJava-49b0d71e-Thread-0] DEBUG loci.formats.ClassList - Could not find loci.formats.in.ZarrReader java.lang.ClassNotFoundException: loci.formats.in.ZarrReader at java.net.URLClassLoader.findClass(URLClassLoader.java:382) at java.lang.ClassLoader.loadClass(ClassLoader.java:419) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:352) at java.lang.ClassLoader.loadClass(ClassLoader.java:352) at java.lang.Class.forName0(Native Method) at java.lang.Class.forName(Class.java:264) at loci.formats.ClassList.parseLine(ClassList.java:196) at loci.formats.ClassList.parseFile(ClassList.java:258) at loci.formats.ClassList.<init>(ClassList.java:138) at loci.formats.ClassList.<init>(ClassList.java:122) at loci.formats.ImageReader.getDefaultReaderClasses(ImageReader.java:80) at io.scif.bf.BioFormatsFormat.cacheReaderClasses(BioFormatsFormat.java:538) at io.scif.bf.BioFormatsFormat.<init>(BioFormatsFormat.java:139) at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method) at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62) at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45) at java.lang.reflect.Constructor.newInstance(Constructor.java:423) at java.lang.Class.newInstance(Class.java:442) at org.scijava.plugin.PluginInfo.createInstance(PluginInfo.java:304) at org.scijava.plugin.DefaultPluginService.createInstance(DefaultPluginService.java:234) at org.scijava.plugin.DefaultPluginService.createInstances(DefaultPluginService.java:223) at org.scijava.plugin.DefaultPluginService.createInstancesOfType(DefaultPluginService.java:214) at io.scif.services.DefaultFormatService.lambda$initialize$0(DefaultFormatService.java:459) at org.scijava.thread.DefaultThreadService.lambda$wrap$1(DefaultThreadService.java:211) at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:511) at java.util.concurrent.FutureTask.run(FutureTask.java:266) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) at java.lang.Thread.run(Thread.java:748) ImageJ version: 2.3.0/1.53f
ij.py.run_macro
¶Running an original ImageJ style macro is as simple as providing the macro code in a string, and the arguments in a dictionary to ij.py.run_macro
. Modify the following cell to print your name, age, and city.
macro = """
#@ String name
#@ int age
#@ String city
#@output Object greeting
greeting = "Hello " + name + ". You are " + age + " years old, and live in " + city + "."
"""
args = {
'name': 'Chuckles',
'age': 13,
'city': 'Nowhere'
}
result = ij.py.run_macro(macro, args)
print(result.getOutput('greeting'))
WARNING:root:Operating in headless mode - the original ImageJ will have limited functionality.
[INFO] script:macro.ijm = [[greeting], [Hello Chuckles. You are 13 years old, and live in Nowhere.]] Hello Chuckles. You are 13 years old, and live in Nowhere.
[java.lang.Enum.toString] [INFO] script:macro.ijm = [[greeting], [Hello Chuckles. You are 13 years old, and live in Nowhere.]]
ij.py.run_script
¶Running scripts in other languages is similar, but you also have to specify the language extension (e.g. 'py', 'ijm', 'js') or the language name (e.g. 'python', 'IJ1 Macro', 'javascipt') for the scripting language it is written in.
language_extension = 'ijm'
result_script = ij.py.run_script(language_extension, macro, args)
print(result_script.getOutput('greeting'))
[INFO] script:script.ijm = [[greeting], [Hello Chuckles. You are 13 years old, and live in Nowhere.]] Hello Chuckles. You are 13 years old, and live in Nowhere.
[java.lang.Enum.toString] [INFO] script:script.ijm = [[greeting], [Hello Chuckles. You are 13 years old, and live in Nowhere.]]
ij.py.run_plugin
¶Finally, running plugins works in the same manner as macros. You simply enter the plugin name as a string and the arguments in a dict. For the few plugins that use ImageJ2 style macros (i.e., explicit booleans in the recorder), set the optional variable ij1_style=False
.
This example works with original ImageJ windows, opening images entirely within ImageJ and then getting the results. Working with original ImageJ windows requires importing another class, which is done using the jimport
function of scyjava.
ij.py.run_macro("""run("Blobs (25K)");""")
blobs = ij.WindowManager.getCurrentImage()
print(blobs)
WARNING:root:Operating in headless mode - the WindowManager class will not be fully functional.
img["blobs.gif" (-3), 8-bit, 256x254x1x1x1]
Now let's view the blobs.
ij.py.show(blobs)
We can now run plugins that require open original ImageJ windows on blobs
plugin = 'Mean'
args = {
'block_radius_x': 10,
'block_radius_y': 10
}
ij.py.run_plugin(plugin, args)
<java object 'org.scijava.script.ScriptModule'>
Next, obtain the current image from the WindowManager
and display the results from the plugin.
result = ij.WindowManager.getCurrentImage()
result = ij.py.show(result)
You can list any active original ImageJ windows with the following command.
print(ij.py.from_java(ij.window().getOpenWindows()))
['blobs.gif']
You can close any original ImageJ windows through the following command.
ij.window().clear()
print(ij.py.from_java(ij.window().getOpenWindows()))
[]