Some useful procedures

There is a very extensive compilation of all the functions available in the macro language on the ImageJ website (http://rsbweb.nih.gov/ij/developer/macro/functions.html). In this section, we are offering a brief explanation of some of the operations that you are most likely to use. Instead of just listing the name of the necessary functions, we will ask some common questions and then answer them using code.

Note that finding out what command does a specific function is very easy: just start the recorder and run the command you are interested on running in your macro. You can then copy and paste the resulting line and modify the parameters accordingly.

Opening an image from a macro

There are two ways to open an image file from your hard disk (or from a URL). For an interactive way (you need input from the user, typically the file path) just run the following line:

open();

A dialog will appear asking you for the file location inside your hard disk. Just double click on it and the image will be opened.

The non-interactive way, in which you know in advance the file location, is very similar:

open(path);

Here path is the location of the file (for example, C:/temp/image1.jpg).

It may happen that you want to store the image path into a variable to open it using a different method (for example, importing a raw image). In that case, we can use the File.openDialog(message) function. It opens a file browser dialog and returns the path of the selected file. The following code does the same by simply calling open(), but will also store the path in the mypath variable using the following code:

mypath = File.openDialog("Select a file");
open(mypath);

Finding out how many images are open

The number of images currently open in the ImageJ system is stored in a variable called nImages. It updates itself every time a new image is opened. Duplicate images are count as a just another image. Try the following macro:

print(nImages); // No images: 0.
run("Dot Blot (7K)");
print(nImages); // One image: 1.
run("Dot Blot (7K)");
print(nImages); // Two images: 2.

As you can see when you run this code, the run("DotBlot(7K)") line causes ImageJ to open the Dot Blot sample image.

Obtaining the dimensions of an image

There are several ways of doing that. If you want individual dimensions, you can use the getHeight() and getWidth() functions. Also, the nSlices variable stores the number of slices in the active stack. If you need all the information at once, you can run the getDimensions(width,height,channels,slices,frames) function. This function is a bit different from the other functions we have already seen. Instead of returning a value, it sets the width variable to the width of the image, the height variable to the height of the image, and so on. That is, after calling it you will have five new variables.

Tip

Be careful while calling the getDimensions function, as they are assigned parameters following that predefined order, and not by name (you cannot call getDimensions(channels,slices,height,width,frames) and expect the result to be consistent with the variable names).

A note on slices, frames, and channels

As you may have noted, the coordinates for width and height of a given image start at 0. An image with a matrix size of 100 x 200 will have the x coordinate ranging from 0 to 99 and y coordinate from 0 to 199. However, the notation for slices, frames, and channels is different, as they always start at 1. Consider the following macro:

run("T1 Head (2.4M, 16-bits)");
for(i = 1; i<= nSlices; i++) {
  Stack.setSlice(i);
  value = getPixel(100, 100);
  print("Pixel (100, 100) in slice", i, "=", value);
  wait(200); // Wait 200 miliseconds
}

Let's stop for a moment on it, as it is using most of the concepts we have learned so far. First, it opens a sample image (T1Head) and then it uses a for loop to iterate through its slices using one of the Stack functions (take a look at the macro functions reference to see more stack operations). Note that the index variable used, i, starts at one and makes the loop run until (and including) its value is equal to nSlices. It then grabs the pixel value placed in the coordinates (100, 100) and prints it. When you run this macro, you will see how ImageJ goes through all the slices of the stack, and the pixel selected values printed in the log window. We have added a small waiting time (200 milliseconds) as the parameter of the wait function, so that you can clearly see what is going on.

Tip

Try this: modify the preceding macro so that it only iterates through the even slices of the image. Also, try changing the starting loop value to 0. You would expect an error message, but it selects slice 1 instead. This may cause an incorrect measurement if you iterate a given image this way, as you will process the first slice twice!

Other useful Stack functions are Stack.setFrame(frame) and Stack.setChannel(channel), which will allow you to select specific frames or channels, as we have just done with the slices.

There are two important aspects to be learned for running the preceding macro:

  • The getPixel(x,y) function grabs the pixel value of the currently selected slice for the provided x and y coordinates. Note that the stack selection is done prior to getting the pixel value, and we are not providing any slice information to the getPixel(x,y)function.
  • The macro system is deeply ingrained with the user interface. The results of the macro functions that affect an image in any given way (filtering, setting pixel values, changing the active slice / channel / frame, and so on) are shown on the screen immediately. Think of a macro as a very fast and efficient user performing the instructions you wrote down.

Selecting a specific image

Macro functions, unless specified, are applied to the image being displayed and selected, as we just saw. It may be the case that you have several images opened and want to apply different operations to each one of them or use information from one to modify another. There are several ways for selecting an opened image from the ImageJ macro language, which are as follows:

  • Using the selectImage(id) function. This function is called with an argument that can mean two different things, depending on its value:
    • If it is a negative number, it is the image ID, an internal ImageJ number that is different for each image. This number is obtained by running getImageID().
    • If it is a positive number, it is the order in which the images were opened. For instance, selectImage(1) will select the image that was opened before any other one, from the list of images currently opened (not really the first one in absolute terms, as the first image opened in that session could have been closed).
  • Using the selectWindow(name) function, where name is a string that contains the window name you want to select.

The following macro opens two images and switches between them using all the approaches explained previously. We recommend running it line-by-line to understand how it works:

// Open two sample images.
run("Clown (14K)");
run("Leaf (36K)");
// How many images are there? You can also see this variable in the debug window
print(nImages + " opened");
// Select the first opened image. This is the clown image, by opening order.
selectImage(1);
// Is it really the clown image?
clownTitle = getTitle();
print("Image selected: " + clownTitle);
// Select an image by name
selectWindow(clownTitle);
// Get the image ID of the selected image. This is a negative number that you normally do not
// know in advance (as opposed to the opening order number).
clownID = getImageID();
print("clown.jpg image ID: " + clownID);
// Select the leaf image (the second image opened).
selectImage(2);
// Go back to the clown image using the image ID, not the opening order
selectImage(clownID);

Speeding up a macro

For complicated operations or processes that involve switching between several images, macros can be quite slow. The best way to speed up your macro is to use the setBatchMode(arg) function. This function stops ImageJ from displaying on the screen the operations being performed on the image, thus allowing the macro to run upto 20 times faster, according to the official documentation. This function receives an argument, which has to be true (for entering the batch mode) or false (for exiting it). When the macro finishes, the batch mode is set to false automatically.

You have to run setBatchMode(true) before opening the image or the images you wish to process to enjoy this speed bump. Setting it after the images are being processed and shown on the screen will have no impact on its execution.

Tip

You also have the option of programming a plugin or use some scripting language instead of a macro. Plugins are a more advanced topic that will be covered in the final two chapters of this book, and they generally require you to have some programming skills. Scripts are not covered in this book, but if you have knowledge in Python, for instance, you might want to take a look at them.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset