// Intersect Count Method for quantitative metallography // // by Christopher Coulon, www.gaiag.net, and Ali Soleimani-Dorcheh, // DECHEMA Research Institute, Frankfurt am Main, Germany. // // This macro is developed to convert a large amount of data from one or more images // to quantitative stereological parameters which helps to analyse three dimensional // characteristics of the microstructure of materials based on two dimensional images. // // The macro utilizes ImageJ tools and provides an automated quantitative method // for phase analysis based on intersect counting method. // The targeted systems are multi-phase systems which have distinct interphase boundaries // including systems containing pores and composite materials. // Binary images are required before using this macro. The macro can process // multiple binary images continiously. It saves the calculations corresponding // to each image in a separate folder. // // For details of usage, please email Chris (chris@gaiag.net) // or Ali (soleimani@dechema.de). var step =50; var angle =0; var name, title, path, dir, resultsDir; var areaFraction; var gridType; var Width, Height, imageArea = 0; var voxelW, voxelH; var lineCount; var lineTotal = 0, ROItotal = 0; var invertImage = true; var timeString; var ANDlinesPercent = 0, ROIpercent = 0; var distance, unit; var totalSum, totalLineCount, noEdgeSum, noEdgeLineCount, edgeParticles; var intersections, wEdgeLines, noEdgeLines; var options = false, start = true; macro "Grid Tool - C00cT1f1aG" {} macro "Grid Tool Options" { path = File.openDialog("Select a File"); dir = File.getParent(path); name = File.getName(path); list = getFileList(dir); start = true; for (i=0; i 0) run("Invert"); } function sumLines() { run("Set Measurements...", " feret's limit redirect=None decimal=5"); run("Analyze Particles...", " clear"); nr = nResults; wEdgeLines = newArray(nr); totalSum = 0; for (i = 0; i < nr; i++) { totalSum += getResult("Feret", i); wEdgeLines[i] = getResult("Feret", i); } totalMean = totalSum / nr; sumDiff = 0; for (i = 0; i < nr; i++) { x = getResult("Feret", i); sumDiff += (x - totalMean)*(x - totalMean); } totalSD = sqrt(sumDiff / (nr - 1)); totalLineCount = nResults; selectWindow("Results"); // saveAs("Results", resultsDir + name + "_allLines.xls"); run("Analyze Particles...", " exclude clear"); nr = nResults; noEdgeLines = newArray(nr); noEdgeSum = 0; for (i = 0; i < nResults; i++) { noEdgeSum += getResult("Feret", i); noEdgeLines[i] = getResult("Feret", i); } noEdgeMean = noEdgeSum / nr; sumDiff = 0; for (i = 0; i < nr; i++) { x = getResult("Feret", i); sumDiff += (x - noEdgeMean)*(x - noEdgeMean); } noEdgeSD = sqrt(sumDiff / (nr - 1)); noEdgeLineCount = nResults; edgeParticles = totalLineCount - noEdgeLineCount; numberOfIntercepts = noEdgeLineCount + (edgeParticles / 2); selectWindow("Results"); // saveAs("Results", resultsDir + name + "_noEdgeLines.xls"); write ("All intercepts = " + totalLineCount); write ("No edge intercepts = " + noEdgeLineCount); write ("Edge intercepts = " + edgeParticles); write ("\n********** All Intercepts **********"); ne = totalLineCount * 2; write ("Total Overlap Length = " + totalSum); write ("Line Intercepts = " + totalLineCount); write ("Intersections = " + ne); write ("Average Length All = " + totalMean); write ("Standard Deviation All = " + totalSD); write ("****************************************"); write ("\n*********** All with Half Edge Intercepts ***********"); intersections = noEdgeLineCount * 2 + edgeParticles; write ("Total Overlap Length = " + totalSum); write ("Line Intercepts = " + numberOfIntercepts); write ("Intersections = " + intersections); write ("****************************************"); write ("\n********** Only No Edge Intercepts **********"); ne = noEdgeLineCount * 2; write ("No Edge Overlap Length = " + noEdgeSum); write ("Line Intercepts = " + noEdgeLineCount); write ("Intersections = " + ne); write ("\nAverage Length non-Edge = " + noEdgeMean); write ("Standard Deviation non-Edge = " + noEdgeSD); write ("****************************************"); return numberOfIntercepts; } function gridOptions() { Dialog.create("Grid"); Dialog.addNumber("Step (in pixels):", step); Dialog.addNumber("Angle (in degrees):", angle); // Dialog.addCheckbox("Set Grid for All", false); Dialog.show; step = Dialog.getNumber(); angle = Dialog.getNumber(); // options = Dialog.getCheckbox(); } function dumpImages() { selectWindow(title); close("\\Others"); } function closeResults() { if (isOpen("Results")) { selectWindow("Results"); run("Close"); } if (isOpen("ROI Manager")) { selectWindow("ROI Manager"); run("Close"); } if (isOpen("Log")) { selectWindow("Log"); run("Close"); } if (isOpen("Threshold")) { selectWindow("Threshold"); run("Close"); } if (isOpen("Debug")) { selectWindow("Debug"); run("Close"); } }