Statistical regional merging from script

beanshell
groovy
Tags: #<Tag:0x00007fb883dbe500> #<Tag:0x00007fb883dbe0c8>

#1

Dear Everyone,

I am currently writing a script in Groovy to find and track bacteria from a microscopy movie. Currently, I am able to do this, and now I am looking for improving the speed and precision. For that purpose, I would like to do some statistical regional merging. So far, I am able to call the function (See code below), but it prompts a dialogue, which makes impossible to run the script in a folder as I would have to click for every file. Therefore, I would like to ask if anyone knows how to manually perform statistical regional merging or how to call the function from a script. Here is my code so far, it pre-process the images, and stores a binary version that would be used for the tracking:

// @File(label="Input directory", description="Select the directory with input images", style="directory") inputDir
// @File(label="Output directory", description="Select the output directory", style="directory") outputDir
// @File(label="Weka model", description="Select the Weka model to apply") modelPath
// @String(label="Result mode",choices={"Labels","Probabilities"}) resultMode
// @int (label= "Transition depth", description ="Gap between moving slides") Depth

import trainableSegmentation.WekaSegmentation
import trainableSegmentation.utils.Utils
import ij.io.FileSaver
import ij.*
import ij.ImagePlus
import ij.WindowManager
import ij.plugin.*
import loci.plugins.BF

// starting time
startTime = System.currentTimeMillis()

// caculate probabilities?
getProbs = resultMode.equals( "Probabilities" )

// create segmentator
segmentator = new WekaSegmentation()
// load classifier
segmentator.loadClassifier( modelPath.getCanonicalPath() )

// get list of input images
listOfFiles = inputDir.listFiles()
for ( i = 0; i < listOfFiles.length; i++ )
{
    // process only files (do not go into sub-folders)
    if( listOfFiles[ i ].isFile() )
    {
        // try to read file as image
        //image = IJ.openImage( listOfFiles[i].getCanonicalPath() )
        listOfFiles = inputDir.listFiles()
        path = listOfFiles[i].getCanonicalPath()
        options="open=["+path+"] view=[Standard ImageJ] color_mode=Default view=[Standard ImageJ] stack_order=XYCZT"
        IJ.run("Bio-Formats Importer",options)
        image = IJ.getImage()

        if( image != null )
        {

            // Resize project, get smaller
            stack = image.getStack()
            n = stack.getSize()

            while  (n % Depth != 0) {
                image.setSlice(n)
                IJ.run(image, "Delete Slice", "")
                n = stack.getSize()
            }

            // Pre-processing

            IJ.run(image, "Subtract Background...", "rolling=50 stack") // Background
            IJ.run(image, "8-bit", "")
            for (k=1; k < n+1; k++) {
                image.setSlice(k)
                ip = stack.getProcessor(k)
                stats = ip.getStatistics() // I should do this step by slide!!
                IJ.run(image, "Subtract...", "value=" + stats.median)
            }
            IJ.run(image, "Enhance Contrast...", "saturated=0.5") // Contrast
            IJ.run(image, "Despeckle", "stack") // Denoise

            // Simplify stack
            int x = n/Depth
            image = new GroupedZProjector().groupZProject(image, 5, Depth)
            IJ.run(image, "8-bit", "")
            IJ.run(image, "Median...", "radius=2.5 stack")

            // apply classifier and get results (0 indicates number of threads is auto-detected)
            result = segmentator.applyClassifier( image, 0, getProbs )

            // Extract cells probabilities
            imp2 = new Duplicator().run(result, 1, 1, 1, 1, 1, x) // I have to adjust this number to the real number of slides
            stats = imp2.getStatistics()
            IJ.run(imp2, "Divide...", "value=" + stats.max + " stack")
            IJ.log("We have arrived to imp2")

            // Multiply probabilities by original image
            ImageCalculator ic = new ImageCalculator()
            image.show()
            ImagePlus imp3 = ic.calculate("Multiply stack", image, imp2)
            IJ.run(imp3, "8-bit", "")
            IJ.log("We have arrived to imp3")
            imp3 = IJ.getImage()

            // Transform to binaries
            IJ.run(imp3, "Subtract...", "value=2 stack")
            IJ.run(imp3, "Median...", "radius=3 stack")
            IJ.run(imp3, "Auto Local Threshold", "method=Phansalkar radius=10 parameter_1=0 parameter_2=0 white stack")

            // Resize to original

            stack2 = imp3.getStack()
            n = stack2.getSize()
            OriginalSize = new ImageStack(512, 512)
            for (nS=1; nS< n + 1; nS++)
            {
                ip = stack2.getProcessor(nS)
                ip2 = ip.duplicate()
                for (d=1; d<  Depth+ 1; d++) {
                    OriginalSize.addSlice("Slice = " + nS, ip2)
                }
            }
            OriginalSize = new ImagePlus("OriginalSize", OriginalSize)

            // Save mask as tif
            outputFileName = "Mask_" + listOfFiles[ i ].getName() + ".tif"
            new FileSaver( OriginalSize ).saveAsTiff( outputDir.getPath() + File.separator + outputFileName )
            //IJ.saveAs(OriginalSize, outputDir.getPath() + File.separator + outputFileName

            result = null
            image = null
            imp2 = null
            imp3 = null
            System.gc()

            IJ.run(imp3, "Close All", "")
        }
    }
}
// print elapsed time
estimatedTime = System.currentTimeMillis() - startTime
IJ.log( "** Finished processing folder in " + estimatedTime + " ms **" )