How can I stack all images recorded from one well in batch mode?

Dear forum!
I wouldn’t say I’m unexperienced with ImageJ scripting, but I have a knot which I cannot solve and for which I hope experienced forum users might be able to help:
I have an input folder with several (between 2 and 7) images recorded for each well of a 96-well plate which I would like to stack. In different experiments, recordings from single wells are missing, so it is not always a complete 96-well-plate. Well position of each image is indicated at the beginning of the file, followed by recording date, time and mode, e.g. for well “1B”: “1B_20181012_183106_249_TRANS0_550nm”. Images from same well differ by the postfix, e.g. “_segmented” or “_EPI” etc. I’d like to batch process the folder with all images and generate stacks containing all images of each well. The 96-well plate has wells from 1A, 1B… to 1H up to 12A, 12B… to 12H.
So far, I found the following script which works, but I need to manually insert the well names for which images are in the input folder which is quite nasty:

dir1 = getDirectory(“Input directory with image files”);
dir2 = getDirectory(“Output directory for stacks”);

list = getFileList(dir1);
list = Array.sort(list);
well_array = newArray(“1B”,“1C”);

//I need to manually introduce the well name here

counter = 0;
setBatchMode(true);
while(counter<=well_array.length-1){

for (i = 0; i < list.length; i++) {
	name_i = list[i];
	name_sub_i = substring(name_i, 0, 6);
	well_i = substring(name_sub_i, 0, lastIndexOf(name_sub_i, "_" ));
	if(endsWith(list[i], ".tif") && well_i==well_array[counter] )
	{
		open(dir1+name_i);
	}
}

run("Images to Stack", "name=Stack title=[] use");
saveAs("Tif", dir2+well_array[counter] + ".tif");
close();
counter = counter+1;

}
setBatchMode(false);

If anyone has an idea or an alternative script which does the job without requiring to manually insert the well names present it would be great help!

How about creating an auto-expand well_array, looping over all files in list, extracting the first two letters (the well position), checking if that position name is already in well_array, if not, add.
setOption(“ExpandableArrays”, boolean)
well_array = newArray;
Then you can loop over the now filled array with well positions.

Hi!
Thanks for your reply - I guess I understand how you would solve that! However, if I use “boolean” I get an undefined variable in return, also I would appreciate some more details as there are not many examples for expandable arrays around.
Thanks again, Ralf

Oh, bummer, just write setOption(“ExpandableArrays”, true), and BOOM, now you have expandable arrays. That is, you don’t have to define the array size at declaration time, you can just keep adding elements at will.
An alternative to expandable arrays is to create a function that adds an element to your array if the value is not yet in the array and returns another array that is larger and contains the element not yet in your array. In either case, create a loop over your file names. To that end, duplicate the loop you already have and change the inner works to extract the first two characters, throw them at your function or add them to your expandable array.

Here is a chatty example that demonstrates a way to achieve your subgoal:

setOption("ExpandableArrays", true);
anArray = newArray();
myArray = addUniqueToArray(anArray,"A1");
myArray = addUniqueToArray(myArray,"A3");
myArray = addUniqueToArray(myArray,"A1");
Array.show(myArray);

function addUniqueToArray(array,element){
	alreadyPresent = false;
	for(index = 0; index < array.length; index++){
		if(array[index] == element){
			alreadyPresent = true;
		}
	}
	if (!alreadyPresent){
		return  Array.concat(array,element);
	}else{
		return array;
	}
}

Now you can loop over the array you have created and which will contain any well name that as at least one image available. I do realise that in this example the nature of expandable arrays is not essential.