Saving each ROI as individual images

Dear all,

I am using imageJ for particle analysis purposes and created a macro to do all the job, after original image opened.

My current need requires a bit of programming and Im afraid it is something I am clueless.

What I want to do is, after creation of ROIs for detected particles by particle analysis tools, (original one or by biovoxxel plugin), I want to crop and save each of these ROIs (listed in ROI manager) from ‘original’ image, as individual .png files named like 'originalfilename'+'00000n.png'
There are 3000 images and total particle count is about 30K, so I cant do this manually.

Can anyone help me on how to make this, programmatically, in imageJ, if its possible at all?

(If it cant be done all at once, I can first run my macro for each image manually, save .roi files with same name, then the program may read this roi file for each image then appy the croppings… Just an idea…)

I appreciate any help.

There are several ways to do this. However a simple suggestion is to simply save the tif with ImageJ which will also save the particle overlays in the tif instead of cropping (do you really need a cropped particle image or is the data sufficient which can be restored from the saved tif?).

If you need to open the particle data later then the following actions are very simple.

If you reopen the stored tif you will see all ROI particles again as overlays which you can enable again with menu command

Image->Overlay->To ROI Manager

Here a macro example (Adjust the paths):

    run("Cell Colony (31K)");
    setAutoThreshold("Default");
    //run("Threshold...");
    run("Close");
    run("Analyze Particles...", "display clear include add");
    saveAs("Tiff", "I:\\Your_Image\\Cell_Colony.tif");
    //Reopen the image and restore all ROI's
    open("I:\\Your_Image\\Cell_Colony.tif");
    run("To ROI Manager");

This macro can then be applied on all images easily with the Batch action, see:

However it is also possible to crop a rectangular particle image from each ROI if this is necessary.

Example:

    // Iterate all ROIs in ROI Manager
    for (i=0; i<roiManager("count"); ++i) {
    	roiManager("Select", i);
    	run("Crop");
        saveAs("Tiff", "I:\\Your_Image\\Cell_Colony_Particle_"+i+".tif");
    }
1 Like

First of all thank you very much for very fast answer, lightened up a bit more.

Yes I do need bounding-box cropped images of each and every particle as individual picture files, since rest of the analysis will not continue in ImageJ. (avg. particle size is like 40x40, although this varies between 20 and 200).

If I am not wrong, the above code seems saving ROIs along with processed image. What I need is to be able to apply these ROIs to the original image. Then I need to save bounding-box images of the particles, only from original (color) image, but the code seems saving processed (B/W) image. Any hopes for this?

Simpy select the original image before you select the ROI and crop.

In the following macro I also made some duplicates to apply the crop on the original data.

This macro creates 669 cropped images from the original image and the ROI data (RGB dummy created from a RGB).

You can extend it easily to apply the same procedure on a folder of images where each image particles could be saved in a special folder. The setBatchMode(true) speeds up the process in this analysis. Adjust the threshold range to your needs and specify the right folder in the macro!

// Load create example RGB from greyscale for demonstration

//Speed up in batch mode
setBatchMode(true)
run("Cell Colony (31K)");
run("RGB Color");
//Make a duplicate from the original
run("Duplicate...", "title=particles");
run("8-bit");
selectWindow("particles");
//Set a threshold
setThreshold(0, 171);
run("Analyze Particles...", "exclude clear include add");
//Select the original which should be cropped
selectWindow("Cell_Colony.jpg");
for (i=0; i<roiManager("count"); ++i) {
    run("Duplicate...", "title=crop");
    roiManager("Select", i);
    run("Crop");
    saveAs("Tiff", "I:\\YourImageFolder_Imagexxxx\\Cell_Colony_Particle_"+(i+1)+".tif");
    close();
     //Next round!
     selectWindow("Cell_Colony.jpg");
}
2 Likes

Well, I started to learn something… Sincere thanks for all the invaluable help. The following code is doing what I want, but this selectWindow() is still a headache.

I tried

selectWindow(filename)

and it failed. Somehow, selectWindow(getTitle()) is working but its first capture is an outline, then the actual picture crops are coming to output directory.
Here is modified code (sorry do not know how to display the code sample in a special box as you did above);

input = "C:\\particles\\";
output = "C:\\partout\\";
function action(input, output, filename) {

        open(input + filename);
// BELOW IS USELESS, IN THE LINES OUT OF FUNCTION BRACKETS { }  ?
		title1=getTitle();
}
setBatchMode(true); 
list = getFileList(input);
for (i = 0; i < list.length; i++)
        action(input, output, list[i]);
setBatchMode(false);
setBatchMode(true)

run("Duplicate...", "title=particles");
run("8-bit");
selectWindow("particles");

setAutoThreshold("Default");
setOption("BlackBackground", false);
run("Analyze Particles...", "size=7-Infinity show=Outlines exclude clear add");
//Select the original which should be cropped
	//THIS IS NOT WORKING
	selectWindow(title1);
// SOMEHOW, BELOW LINE IS WORKING
selectWindow(getTitle());
for (i=0; i<roiManager("count"); ++i) {
    run("Duplicate...", "title=crop");
    roiManager("Select", i);
    run("Crop");
    saveAs("Tiff", output+"The_Particle_"+(i+1)+".tif");
    close();
     //Next round!
     selectWindow(getTitle());
}

There were some errors in the script.
The following macro creates a separate folder for each image ROI croppings.

setBatchMode(true);
input = "C:\\particles\\";
output = "C:\\partout\\";
list = getFileList(input);

for (i = 0; i < list.length; i++){
        print(input + list[i]);
        open(input + list[i]);
        mainTitle=getTitle();
        dirCropOutput=output+File.separator+mainTitle;
        File.makeDirectory(dirCropOutput);     
        run("Duplicate...", "title=particles");
        run("8-bit");
        selectWindow("particles");
        setAutoThreshold("Default");
        setOption("BlackBackground", false);
        run("Analyze Particles...", "size=0-Infinity exclude clear add");

        selectWindow(mainTitle);

        for (u=0; u<roiManager("count"); ++u) {
            run("Duplicate...", "title=crop");
            roiManager("Select", u);
            run("Crop");
            saveAs("Tiff", dirCropOutput+File.separator+"The_Particle_"+(u+1)+".tif");
            close();
             //Next round!
             selectWindow(mainTitle);
        }
        close();
        selectWindow("particles");
        close();
       // print("finished");    
}
4 Likes

Marvellous ! Thank you so much ! Saving to individual directories is perfect. Actually, after a lot of struggling whole night, I managed to made it happen too, (minus directory saving), but the code was twice longer :slight_smile: )

One last question, analyse particles command has an option to display results. A “results” window opens, providing data about every particle. Is it possible to save this table, to the related directory, (for ex., to the directory created for the particles of processed image, above) ?

Again, sincere thanks !

Yes you can do this with:

selectWindow("Results");
saveAs("Results", dirCropOutput+File.separator+"Results.xls");

Here the revised script which opens the results table in the analyze particles action to store the results

setBatchMode(true);
input = "C:\\particles\\";
output = "C:\\partout\\";
list = getFileList(input);

for (i = 0; i < list.length; i++){
        //print(input + list[i]);
        open(input + list[i]);
        mainTitle=getTitle();
        dirCropOutput=output+File.separator+mainTitle;
        File.makeDirectory(dirCropOutput);     
        run("Duplicate...", "title=particles");
        run("8-bit");
        selectWindow("particles");
        setAutoThreshold("Default");
        setOption("BlackBackground", false);
        run("Analyze Particles...", "size=0-Infinity display exclude clear add");
        selectWindow("Results");
        saveAs("Results", dirCropOutput+File.separator+"Results.xls");
        run("Close"); 
        selectWindow(mainTitle);

        for (u=0; u<roiManager("count"); ++u) {
            run("Duplicate...", "title=crop");
            roiManager("Select", u);
            run("Crop");
            saveAs("Tiff", dirCropOutput+File.separator+"The_Particle_"+(u+1)+".tif");
            close();
             //Next round!
             selectWindow(mainTitle);
        }
        close();
        selectWindow("particles");
        close();
        //print("finished");    
}
3 Likes

Thank you again, much simpler then I thought… And above codes become great lecture materials for me to train myself on this macro language :slight_smile:

Hi Bio7

I modified you macro a little for my needs (i am completely new to ImageJ and have to admit that I have no knowledge in Java whatsoever).
I get it to work that it outputs the particles, but at the end I get an error message saying: File saving error (IOException):

furthermore some particles are outputted twice or more. It saves also black images without particles on it and the batch process runs forever.

setBatchMode(true);
input = “C:\particles\”;
output = “C:\partout\”;
list = getFileList(input);

for (i = 0; i < list.length; i++){
print(input + list[i]);
open(input + list[i]);
mainTitle=getTitle();
dirCropOutput=output+File.separator+mainTitle;
File.makeDirectory(dirCropOutput);
run(“Duplicate…”, “title=particles”);

    run("Find Edges");
    run("Smooth");
    run("Smooth");
    run("Smooth");
    run("Enhance Contrast...", "saturated=0.1");
    run("8-bit");
    selectWindow("particles");
    setAutoThreshold("MaxEntropy");
    setOption("BlackBackground", false);
    run("Convert to Mask");
    run("Invert");
    run("Analyze Particles...", "size=110-Infinity pixel show=Outlines add");

    selectWindow(mainTitle);

    for (u=0; u<roiManager("count"); ++u) {
        run("Duplicate...", "title=crop");
        roiManager("Select", u);
        run("To Bounding Box");
        run("Enlarge...", "enlarge=30 pixel");
        run("Crop");
        saveAs("Tiff", dirCropOutput+File.separator+"The_Particle_"+(u+1)+".tif");
        close();
         //Next round!
         selectWindow(mainTitle);
    }
    close();
    selectWindow("particles");
    close();
   // print("finished");    

}

Have you an idea what´s wrong?

link to my original post:

Many thanks in advance!
Cosmo

Edit:
I found out what the problem is.
…First of all I found out that the error message is gone if I start the script outside of ImageJ (when ImageJ isn’t running).
The other problem remains, but at least i know now what the issue is. Maybe some one can help me to solve it? :relaxed:
When ImageJ is processing more than one image, it does not clear the ROI Manager when going to the next image, so when the second image is processed, the old ROIs are still in memory and ImageJ is thinking that there is a particle were in reality no particle is.