def cvt_32_bit_to_8_bit(imp): """ cvt_32_bit_to_8_bit(imp) Convert a 32 bit image to an 8-bit grayscale Parameters ========== imp: ImagePlus The ImagePlus of a 32 bit/px image to convert Returns ======= wrk: ImagePlus The ImagePlus with the 8-bit/px image """ imp.show() wrk = imp.duplicate() ic = ImageConverter(wrk) ic.convertToGray8() title = imp.getTitle() wrk.setTitle(title + "_g8") wrk.updateImage() return wrk
def do_projection(self, channel, proj_type=None): proj = ZProjector() ## create projection class if proj_type is None: if self.do_z[channel] == "MAX": proj.setMethod(ZProjector.MAX_METHOD) elif self.do_z[channel] == "AVG": proj.setMethod(ZProjector.AVG_METHOD) else: print "Dont know how to project this way" print "Just using a single slice for images!!" return None else: if proj_type == "MAX": proj.setMethod(ZProjector.MAX_METHOD) elif proj_type == "AVG": proj.setMethod(ZProjector.AVG_METHOD) else: print "Dont know how to project this way" print "Just using a single slice for images!!" return None proj.setImage(self.stack_imps[channel]) proj.doProjection() projection = proj.getProjection() conv = ImageConverter(projection) conv.convertToGray16() conv.setDoScaling(False) self.projections[channel] = projection self.projections_done[channel] = self.do_z[channel]
def run(): helpText = "This program will batch convert any tif image to 8-bit greyscale, " + \ "and empty calibration infomation.\n\n" + \ ">> Press OK to Select a directory of TIFF images." MessageDialog(IJ.getInstance(), "Empty Calibration Guide", helpText) srcDir = DirectoryChooser("Chose Source Dir").getDirectory() if srcDir is None: IJ.log("Choose Dir Canceled!") return for root, directories, filenames in os.walk(srcDir): for filename in filenames: if not filename.endswith(".tif"): continue imgPath = os.path.join(root, filename) outPath = os.path.join(root, "decal-" + filename) imp = IJ.openImage(imgPath) imp.setCalibration(Calibration()) ic = ImageConverter(imp) ic.convertToGray8() IJ.saveAsTiff(imp, outPath) print "removed calibration and saved to ", os.path.basename( outPath)
def previewDisplaySettings(image, title, zoom, cal): """Apply wanted settings for previews""" ImageConverter.setDoScaling(0) ImageConverter(image).convertToGray16() image.show() IJ.run("glasbey_on_dark") IJ.setMinAndMax(image, 0, 255) image.setTitle(title) image.setCalibration(cal) IJ.run("Set... ", "zoom=" + str(zoom))
def process(imp): try: IJ.run(imp, "Subtract Background...", "rolling=50"); IJ.run(imp, "Subtract Background...", "rolling=50"); ImageConverter.setDoScaling(True); IJ.run(imp, "32-bit", ""); IJ.run(imp, "Smooth", ""); IJ.setAutoThreshold(imp, "Default dark"); IJ.run(imp, "NaN Background", ""); return imp; except(AttributeError): print("error processing!");
def apply_threshold(imp, method='Otsu', background_threshold='dark', stackopt=False, corrf=1.0): # one threshold value for the whole stack with correction if stackopt: # create argument string for the IJ.setAutoThreshold thcmd = method + ' ' + background_threshold + ' stack' # set threshold and get the lower threshold value IJ.setAutoThreshold(imp, thcmd) ip = imp.getProcessor() # get the threshold value and correct it lowth = ip.getMinThreshold() lowth_corr = int(round(lowth * corrf, 0)) # process stack with corrected threshold value imp = ThresholdTools.apply_threshold_stack_corr(imp, lowth_corr, method=method) # threshold slice-by-slice with correction if not stackopt: # get the stack stack = imp.getStack() # get the stack within the ImagePlus nslices = stack.getSize() # get the number of slices print('Slices: ' + str(nslices)) print('Thresholding slice-by-slice') for index in range(1, nslices + 1): ip = stack.getProcessor(index) # get the histogramm hist = ip.getHistogram() # get the threshold value lowth = ThresholdTools.apply_autothreshold(hist, method=method) lowth_corr = int(round(lowth * corrf, 0)) ip.threshold(lowth_corr) # convert to 8bit without rescaling ImageConverter.setDoScaling(False) ImageConverter(imp).convertToGray8() return imp
def apply_threshold_stack_corr(imp, lowth_corr): # get the stacks stack = imp.getStack() nslices = stack.getSize() for index in range(1, nslices + 1): ip = stack.getProcessor(index) ip.threshold(lowth_corr) # convert to 8bit without rescaling ImageConverter.setDoScaling(False) ImageConverter(imp).convertToGray8() return imp
def edm_watershed(imp): # get the image processor ip = imp.getProcessor() if ip.isBinary is False: # convert to 8bit without rescaling ImageConverter.setDoScaling(False) ImageConverter(imp).convertToGray8() else: edm = EDM() edm.setup("watershed", None) edm.run(ip) return imp
def open_images(in_folder): #open Red folder for i in os.listdir(os.path.join(in_folder, "Red")): file_path = os.path.join(in_folder, "Red", i) if os.path.isfile(file_path) and i.endswith(".tif"): print(i) cur_img_red = IJ.openImage(file_path) nslices_red = cur_img_red.getStack().getSize( ) # get the number slices in stack within the ImagePlus #open phase folder for i in os.listdir(os.path.join(in_folder, "Phase")): file_path = os.path.join(in_folder, "Phase", i) if os.path.isfile(file_path) and i.endswith(".tif"): print(i) cur_img_phase = IJ.openImage(file_path) nslices_phase = cur_img_phase.getStack().getSize( ) # get the number slices in stack within the ImagePlus if nslices_red != nslices_phase: sys.exit("Red and phase channel have unequal number of images!") timepoints = nslices_red ImageConverter(cur_img_phase).convertToGray16() comp_stack_img = RGBStackMerge.mergeChannels( [cur_img_red, None, None, cur_img_phase, None, None, None], True) return (comp_stack_img, timepoints)
def Weka_Segm(dirs): """ Loads trained classifier and segments cells """ """ in aligned images according to training. """ # Define reference image for segmentation (default is timepoint000). w_train = os.path.join(dirs["Composites_Aligned"], "Timepoint000.tif") trainer = IJ.openImage(w_train) weka = WekaSegmentation() weka.setTrainingImage(trainer) # Select classifier model. weka.loadClassifier(str(classifier)) weka.applyClassifier(False) segmentation = weka.getClassifiedImage() segmentation.show() # Convert image to 8bit ImageConverter(segmentation).convertToRGB() ImageConverter(segmentation).convertToGray8() # Threshold segmentation to soma only. hist = segmentation.getProcessor().getHistogram() lowth = Auto_Threshold.IJDefault(hist) segmentation.getProcessor().threshold(lowth) segmentation.getProcessor().setThreshold(0, 0, ImageProcessor.NO_LUT_UPDATE) segmentation.getProcessor().invert() segmentation.show() # Run Watershed Irregular Features plugin, with parameters. IJ.run(segmentation, "Watershed Irregular Features", "erosion=20 convexity_treshold=0 separator_size=0-Infinity") # Make selection and add to RoiManager. RoiManager() rm = RoiManager.getInstance() rm.runCommand("reset") roi = ThresholdToSelection.run(segmentation) segmentation.setRoi(roi) rm.addRoi(roi) rm.runCommand("Split")
def run(): helpText = "This program will batch convert any tif image to 8-bit greyscale, " + \ "and empty calibration infomation.\n\n" + \ ">> Press OK to Select a directory of TIFF images." MessageDialog(IJ.getInstance(),"Empty Calibration Guide", helpText) srcDir = DirectoryChooser("Chose Source Dir").getDirectory() if srcDir is None: IJ.log("Choose Dir Canceled!") return for root, directories, filenames in os.walk(srcDir): for filename in filenames: if not filename.endswith(".tif"): continue imgPath = os.path.join(root, filename) outPath = os.path.join(root, "decal-" + filename) imp = IJ.openImage(imgPath) imp.setCalibration(Calibration()) ic = ImageConverter(imp) ic.convertToGray8() IJ.saveAsTiff(imp, outPath) print "removed calibration and saved to ", os.path.basename(outPath)
def convert(filepath, targetFolder): imp = IJ.openImage(filepath) if imp.getType() == ImagePlus.GRAY32: ic = ImageConverter(imp) ic.setDoScaling(False) ic.convertToGray16() filename = os.path.basename(filepath) writeZip(imp, os.path.join(targetFolder, filename), title=filename) else: syncPrint("Not a 32-bit image: " + filename)
def convertAndSaveFile(fullFilePath, convertTo8Bit=False, allowOverwrite=False): """ """ print(' convertAndSaveFile() fullFilePath:', fullFilePath) folderPath, fileName = os.path.split(fullFilePath) fileNameNoExtension = os.path.splitext(fileName)[0] saveFileNoExtension = os.path.join(folderPath, fileNameNoExtension) # # load file and build a dict of parameters like (channels, pixels, voxels) myFileInfo, imp = bSimpleFileInfo.myLoadFile(fullFilePath, doShow=True) if convertTo8Bit: # from (ImagePlus.GRAY8, ImagePlus.GRAY16, ImagePlus.GRAY32, ImagePlus.COLOR_256 or ImagePlus.COLOR_RGB) myType = imp.getType() if myType in [1,2]: ic = ImageConverter(imp) # converts channelImp in place scaleConversions = True ic.setDoScaling(scaleConversions) # scales inensities to fill 0...255 ic.convertToGray8() # # split channels channelArray = ChannelSplitter.split(imp) # returns an array of imp for channelIdx, channelImp in enumerate(channelArray): # channelImp is an imp, this will NOT have fileinfo (we just created it) #channelImp.show() saveFilePath = saveFileNoExtension + '_ch' + str(channelIdx+1) + '.tif' print(' ch:', channelIdx+1, 'saveFilePath:', saveFilePath) if not allowOverwrite and os.path.isfile(saveFilePath): print(' . not saving, file already exists', saveFilePath) else: IJ.save(channelImp, saveFilePath) return myFileInfo
def process(subFolder, outputDirectory, filename): imp = IJ.openImage(inputDirectory + subFolder + '/' + filename) imp.show() IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) ic = ImageConverter(imp) dup = imp.duplicate() dup_title = dup.getTitle() ic.convertToGray8() imp.updateAndDraw() IJ.run("Threshold...") IJ.setThreshold(218, 245) IJ.run(imp, "Convert to Mask", "") rm = RoiManager() imp.getProcessor().setThreshold(0, 0, ImageProcessor.NO_LUT_UPDATE) boundroi = ThresholdToSelection.run(imp) rm.addRoi(boundroi) imp.changes = False imp.close() images = [None] * 5 intensities = [None] * 5 blobsarea = [None] * 5 blobsnuclei = [None] * 5 cells = [None] * 5 bigareas = [None] * 5 IJ.run(dup, "Colour Deconvolution", "vectors=[H DAB]") images[0] = getImage(dup_title + "-(Colour_1)") images[1] = getImage(dup_title + "-(Colour_2)") images[2] = getImage(dup_title + "-(Colour_3)") images[2].close() for chan in channels: v, x = chan imp = images[x] imp.show() for roi in rm.getRoiManager().getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.MEAN | Measurements.AREA) intensities[x] = stats.mean bigareas[x] = stats.area rm.runCommand(imp, "Show None") rm.close() # Opens the ch00 image and sets default properties imp = images[0].duplicate() IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) # Sets the threshold and watersheds. for more details on image processing, see https://imagej.nih.gov/ij/developer/api/ij/process/ImageProcessor.html imp.show() setTempCurrentImage(imp) ic = ImageConverter(imp) imp.updateAndDraw() IJ.run(imp, "Gaussian Blur...", "sigma=" + str(blur)) imp.updateAndDraw() imp.show() IJ.run("Threshold...") IJ.setThreshold(30, lowerBounds[0]) if displayImages: imp.show() WaitForUserDialog( "Title", "Adjust threshold for nuclei. Current region is: " + region).show() IJ.run(imp, "Convert to Mask", "") # Counts and measures the area of particles and adds them to a table called areas. Also adds them to the ROI manager table = ResultsTable() roim = RoiManager() pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 5, 9999999999999999, 0.05, 1.0) pa.setHideOutputImage(True) imp = IJ.getImage() # imp.getProcessor().invert() pa.analyze(imp) imp.changes = False imp.close() areas = table.getColumn(0) # This loop goes through the remaining channels for the other markers, by replacing the ch00 at the end with its corresponding channel # It will save all the area fractions into a 2d array called areaFractionsArray areaFractionsArray = [None] * 5 maxThresholds = [] for chan in channels: v, x = chan # Opens each image and thresholds imp = images[x] IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) imp.show() setTempCurrentImage(imp) ic = ImageConverter(imp) ic.convertToGray8() imp.updateAndDraw() rm.runCommand(imp, "Show None") rm.runCommand(imp, "Show All") rm.runCommand(imp, "Show None") imp.show() IJ.selectWindow(imp.getTitle()) IJ.run("Threshold...") IJ.setThreshold(20, lowerBounds[x]) if displayImages: WaitForUserDialog( "Title", "Adjust threshold for " + v + ". Current region is: " + region).show() ip = imp.getProcessor() maxThresholds.append(ip.getMaxThreshold()) IJ.run(imp, "Convert to Mask", "") # Measures the area fraction of the new image for each ROI from the ROI manager. areaFractions = [] for roi in roim.getRoiManager().getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA_FRACTION) areaFractions.append(stats.areaFraction) # Saves the results in areaFractionArray areaFractionsArray[x] = areaFractions roim.close() for chan in channels: v, x = chan imp = images[x] imp.deleteRoi() imp.updateAndDraw() setTempCurrentImage(imp) roim = RoiManager() pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 15, 9999999999999999, 0.2, 1.0) pa.analyze(imp) blobs = [] cell = [] for roi in roim.getRoiManager().getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA) blobs.append(stats.area) if stats.area > tooSmallThresholdDAB and stats.area < tooBigThresholdDAB: cell.append(stats.area) blobsarea[x] = sum(blobs) blobsnuclei[x] = len(blobs) cells[x] = len(cell) imp.changes = False imp.close() roim.reset() roim.close() # Creates the summary dictionary which will correspond to a single row in the output csv, with each key being a column summary = {} summary['Image'] = filename summary['Directory'] = subFolder # Adds usual columns summary['size-average'] = 0 summary['#nuclei'] = 0 summary['all-negative'] = 0 summary['too-big-(>' + str(tooBigThreshold) + ')'] = 0 summary['too-small-(<' + str(tooSmallThreshold) + ')'] = 0 # Creates the fieldnames variable needed to create the csv file at the end. fieldnames = [ 'Directory', 'Image', 'size-average', 'too-big-(>' + str(tooBigThreshold) + ')', 'too-small-(<' + str(tooSmallThreshold) + ')', '#nuclei', 'all-negative' ] for row in info: if row['Animal ID'] == filename.replace('s', '-').replace( 'p', '-').split('-')[0]: for key, value in row.items(): fieldnames.insert(0, key) summary[key] = value # Adds the columns for each individual marker (ignoring Dapi since it was used to count nuclei) summary["tissue-area"] = bigareas[0] fieldnames.append("tissue-area") for chan in channels: v, x = chan summary[v + "-HEMO-cells"] = 0 fieldnames.append(v + "-HEMO-cells") summary[v + "-intensity"] = intensities[x] fieldnames.append(v + "-intensity") summary[v + "-area"] = blobsarea[x] fieldnames.append(v + "-area") summary[v + "-area/tissue-area"] = blobsarea[x] / bigareas[0] fieldnames.append(v + "-area/tissue-area") summary[v + "-particles"] = blobsnuclei[x] fieldnames.append(v + "-particles") summary[v + "-cells"] = cells[x] fieldnames.append(v + "-cells") summary[v + "-particles/tissue-area"] = blobsnuclei[x] / bigareas[0] fieldnames.append(v + "-particles/tissue-area") fieldnames.append(v + "-HEMO-Cells/tissue-area") # Adds the column for colocalization between first and second marker if len(channels) > 2: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-positive') # Adds the columns for colocalization between all three markers if len(channels) > 3: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[2][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive') # Loops through each particle and adds it to each field that it is True for. areaCounter = 0 for z, area in enumerate(areas): if area > tooBigThreshold: summary['too-big-(>' + str(tooBigThreshold) + ')'] += 1 elif area < tooSmallThreshold: summary['too-small-(<' + str(tooSmallThreshold) + ')'] += 1 else: summary['#nuclei'] += 1 areaCounter += area temp = 0 for chan in channels: v, x = chan if areaFractionsArray[x][z] > areaFractionThreshold[0]: summary[chan[0] + '-HEMO-cells'] += 1 if x != 0: temp += 1 if temp == 0: summary['all-negative'] += 1 if len(channels) > 2: if areaFractionsArray[1][z] > areaFractionThreshold[1]: if areaFractionsArray[2][z] > areaFractionThreshold[2]: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] += 1 if len(channels) > 3: if areaFractionsArray[1][z] > areaFractionThreshold[1]: if areaFractionsArray[3][z] > areaFractionThreshold[3]: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[2][z] > areaFractionThreshold[2]: if areaFractionsArray[3][z] > areaFractionThreshold[3]: summary[channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[1][z] > areaFractionThreshold[1]: summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 # Calculate the average of the particles sizes for chan in channels: v, x = chan summary[v + "-cells/tissue-area"] = summary[v + "-cells"] / bigareas[0] if float(summary['#nuclei']) > 0: summary['size-average'] = round(areaCounter / summary['#nuclei'], 2) if displayImages: fieldnames = ["Directory", "Image"] for chan in channels: v, x = chan summary[v + "-threshold"] = maxThresholds[x] fieldnames.append(v + "-threshold") allMaxThresholds[v + "-" + region].append(maxThresholds[x]) # Opens and appends one line on the final csv file for the subfolder (remember that this is still inside the loop that goes through each image) with open(outputName, 'a') as csvfile: writer = csv.DictWriter(csvfile, fieldnames=fieldnames, extrasaction='ignore', lineterminator='\n') if os.path.getsize(outputName) < 1: writer.writeheader() writer.writerow(summary)
def process(subFolder, outputDirectory, filename): #IJ.close() imp = IJ.openImage(inputDirectory + subFolder + '/' + rreplace(filename, "_ch00.tif", ".tif")) imp.show() # Get the pixel values from the xml file for file in os.listdir(inputDirectory + subFolder): if file.endswith('.xml'): xml = os.path.join(inputDirectory + subFolder, file) xml = "C:/Users/Harris/Desktop/test_xml_for_parsing_pixel.xml" element_tree = ET.parse(xml) root = element_tree.getroot() for dimensions in root.iter('DimensionDescription'): num_pixels = int(dimensions.attrib['NumberOfElements']) if dimensions.attrib['Unit'] == "m": length = float(dimensions.attrib['Length']) * 1000000 else: length = float(dimensions.attrib['Length']) pixel_length = length / num_pixels else: pixel_length = 0.8777017 IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=" + str(pixel_length) + " pixel_height=" + str(pixel_length) + " voxel_depth=25400.0508001") ic = ImageConverter(imp) ic.convertToGray8() #IJ.setThreshold(imp, 2, 255) #Automatically selects the area of the organoid based on automated thresholding and creates a mask to be applied on #all other images IJ.setAutoThreshold(imp, "Mean dark no-reset") IJ.run(imp, "Convert to Mask", "") IJ.run(imp, "Analyze Particles...", "size=100000-Infinity add select") rm = RoiManager.getInstance() num_roi = rm.getCount() for i in num_roi: imp = getCurrentImage() rm.select(imp, i) IJ.setBackgroundColor(0, 0, 0) IJ.run(imp, "Clear Outside", "") IJ.run(imp, "Convert to Mask", "") IJ.run(imp, "Remove Outliers...", "radius=5" + " threshold=50" + " which=Dark") IJ.run(imp, "Remove Outliers...", "radius=5" + " threshold=50" + " which=Bright") # Save the mask and open it IJ.saveAs("tiff", inputDirectory + '/mask' + i) mask = IJ.openImage(inputDirectory + '/mask' + i + '.tif') if not displayImages: imp.changes = False imp.close() images = [None] * 5 intensities = [None] * 5 blobsarea = [None] * 5 blobsnuclei = [None] * 5 bigAreas = [None] * 5 imp.close() # Loop to open all the channel images for chan in channels: v, x = chan images[x] = IJ.openImage(inputDirectory + subFolder + '/' + rreplace(filename, "_ch00.tif", "_ch0" + str(x) + ".tif")) # Apply Mask on all the images and save them into an array apply_mask = ImageCalculator() images[x] = apply_mask.run("Multiply create 32 bit", mask, images[x]) ic = ImageConverter(images[x]) ic.convertToGray8() imp = images[x] # Calculate the intensities for each channel as well as the organoid area for roi in rm.getRoisAsArray(): imp.setRoi(roi) stats_i = imp.getStatistics(Measurements.MEAN | Measurements.AREA) intensities[x] = stats_i.mean bigAreas[x] = stats_i.area rm.close() # Opens the ch00 image and sets default properties #Get the pixel values from the xml file for file in os.listdir(subFolder): if file.endswith('.xml'): xml = os.path.join(inputDirectory + subFolder, file) xml = "C:/Users/Harris/Desktop/test_xml_for_parsing_pixel.xml" element_tree = ET.parse(xml) root = element_tree.getroot() for dimensions in root.iter('DimensionDescription'): num_pixels = int(dimensions.attrib['NumberOfElements']) if dimensions.attrib['Unit'] == "m": length = float(dimensions.attrib['Length']) * 1000000 else: length = float(dimensions.attrib['Length']) pixel_length = length / num_pixels else: pixel_length = 0.8777017 imp = IJ.openImage(inputDirectory + subFolder + '/' + filename) imp = apply_mask.run("Multiply create 32 bit", mask, imp) IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=" + str(pixel_length) + "pixel_height=" + str(pixel_length) + "voxel_depth=25400.0508001") # Sets the threshold and watersheds. for more details on image processing, see https://imagej.nih.gov/ij/developer/api/ij/process/ImageProcessor.html ic = ImageConverter(imp) ic.convertToGray8() IJ.run(imp, "Remove Outliers...", "radius=2" + " threshold=50" + " which=Dark") IJ.run(imp, "Gaussian Blur...", "sigma=" + str(blur)) IJ.setThreshold(imp, lowerBounds[0], 255) if displayImages: imp.show() IJ.run(imp, "Convert to Mask", "") IJ.run(imp, "Watershed", "") if not displayImages: imp.changes = False imp.close() # Counts and measures the area of particles and adds them to a table called areas. Also adds them to the ROI manager table = ResultsTable() roim = RoiManager(True) ParticleAnalyzer.setRoiManager(roim) pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 15, 9999999999999999, 0.2, 1.0) pa.setHideOutputImage(True) # imp = impM # imp.getProcessor().invert() pa.analyze(imp) areas = table.getColumn(0) # This loop goes through the remaining channels for the other markers, by replacing the ch00 at the end with its corresponding channel # It will save all the area fractions into a 2d array called areaFractionsArray areaFractionsArray = [None] * 5 for chan in channels: v, x = chan # Opens each image and thresholds imp = images[x] IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) ic = ImageConverter(imp) ic.convertToGray8() IJ.setThreshold(imp, lowerBounds[x], 255) if displayImages: imp.show() WaitForUserDialog("Title", "Adjust Threshold for Marker " + v).show() IJ.run(imp, "Convert to Mask", "") # Measures the area fraction of the new image for each ROI from the ROI manager. areaFractions = [] for roi in roim.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA_FRACTION) areaFractions.append(stats.areaFraction) # Saves the results in areaFractionArray areaFractionsArray[x] = areaFractions roim.close() for chan in channels: v, x = chan imp = images[x] imp.deleteRoi() roim = RoiManager(True) ParticleAnalyzer.setRoiManager(roim) pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 15, 9999999999999999, 0.2, 1.0) pa.analyze(imp) blobs = [] for roi in roim.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA) blobs.append(stats.area) blobsarea[x] = sum( blobs ) #take this out and use intial mask tissue area from the beginning blobsnuclei[x] = len(blobs) if not displayImages: imp.changes = False imp.close() roim.reset() roim.close() imp.close() # Creates the summary dictionary which will correspond to a single row in the output csv, with each key being a column summary = {} summary['Image'] = filename summary['Directory'] = subFolder # Adds usual columns summary['size-average'] = 0 summary['#nuclei'] = 0 summary['all-negative'] = 0 summary['too-big-(>' + str(tooBigThreshold) + ')'] = 0 summary['too-small-(<' + str(tooSmallThreshold) + ')'] = 0 # Creates the fieldnames variable needed to create the csv file at the end. fieldnames = [ 'Name', 'Directory', 'Image', 'size-average', 'too-big-(>' + str(tooBigThreshold) + ')', 'too-small-(<' + str(tooSmallThreshold) + ')', '#nuclei', 'all-negative' ] # Adds the columns for each individual marker (ignoring Dapi since it was used to count nuclei) summary["organoid-area"] = bigAreas[x] fieldnames.append("organoid-area") for chan in channels: v, x = chan summary[v + "-positive"] = 0 fieldnames.append(v + "-positive") summary[v + "-intensity"] = intensities[x] fieldnames.append(v + "-intensity") summary[v + "-blobsarea"] = blobsarea[x] fieldnames.append(v + "-blobsarea") summary[v + "-blobsnuclei"] = blobsnuclei[x] fieldnames.append(v + "-blobsnuclei") # Adds the column for colocalization between first and second marker if len(channels) > 2: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-positive') # Adds the columns for colocalization between all three markers if len(channels) > 3: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[2][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive') # Loops through each particle and adds it to each field that it is True for. areaCounter = 0 for z, area in enumerate(areas): log.write(str(area)) log.write("\n") if area > tooBigThreshold: summary['too-big-(>' + str(tooBigThreshold) + ')'] += 1 elif area < tooSmallThreshold: summary['too-small-(<' + str(tooSmallThreshold) + ')'] += 1 else: summary['#nuclei'] += 1 areaCounter += area temp = 0 for chan in channels: v, x = chan if areaFractionsArray[x][z] > areaFractionThreshold[ 0]: # theres an error here im not sure why. i remember fixing it before summary[chan[0] + '-positive'] += 1 if x != 0: temp += 1 if temp == 0: summary['all-negative'] += 1 if len(channels) > 2: if areaFractionsArray[1][z] > areaFractionThreshold[1]: if areaFractionsArray[2][z] > areaFractionThreshold[2]: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] += 1 if len(channels) > 3: if areaFractionsArray[1][z] > areaFractionThreshold[1]: if areaFractionsArray[3][z] > areaFractionThreshold[3]: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[2][z] > areaFractionThreshold[2]: if areaFractionsArray[3][z] > areaFractionThreshold[3]: summary[channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[1][z] > areaFractionThreshold[1]: summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 # Calculate the average of the particles sizes if float(summary['#nuclei']) > 0: summary['size-average'] = round(areaCounter / summary['#nuclei'], 2) # Opens and appends one line on the final csv file for the subfolder (remember that this is still inside the loop that goes through each image) with open(outputDirectory + "/" + outputName + ".csv", 'a') as csvfile: writer = csv.DictWriter(csvfile, fieldnames=fieldnames, extrasaction='ignore', lineterminator='\n') if os.path.getsize(outputDirectory + "/" + outputName + ".csv") < 1: writer.writeheader() writer.writerow(summary) IJ.run(imp, "Close All", "")
def process(subFolder, outputDirectory, filename): imp = IJ.openImage(inputDirectory + subFolder + '/' + rreplace(filename, "_ch00.tif", ".tif")) IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) ic = ImageConverter(imp) ic.convertToGray8() IJ.setThreshold(imp, 2, 255) IJ.run(imp, "Convert to Mask", "") IJ.run(imp, "Remove Outliers...", "radius=5" + " threshold=50" + " which=Dark") IJ.run(imp, "Remove Outliers...", "radius=5" + " threshold=50" + " which=Bright") imp.getProcessor().invert() rm = RoiManager(True) imp.getProcessor().setThreshold(0, 0, ImageProcessor.NO_LUT_UPDATE) boundroi = ThresholdToSelection.run(imp) rm.addRoi(boundroi) if not displayImages: imp.changes = False imp.close() images = [None] * 5 intensities = [None] * 5 blobsarea = [None] * 5 blobsnuclei = [None] * 5 bigAreas = [None] * 5 for chan in channels: v, x = chan images[x] = IJ.openImage(inputDirectory + subFolder + '/' + rreplace(filename, "_ch00.tif", "_ch0" + str(x) + ".tif")) imp = images[x] for roi in rm.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.MEAN | Measurements.AREA) intensities[x] = stats.mean bigAreas[x] = stats.area rm.close() # Opens the ch00 image and sets default properties imp = IJ.openImage(inputDirectory + subFolder + '/' + filename) IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) # Sets the threshold and watersheds. for more details on image processing, see https://imagej.nih.gov/ij/developer/api/ij/process/ImageProcessor.html ic = ImageConverter(imp) ic.convertToGray8() IJ.run(imp, "Remove Outliers...", "radius=2" + " threshold=50" + " which=Dark") IJ.run(imp, "Gaussian Blur...", "sigma=" + str(blur)) IJ.setThreshold(imp, lowerBounds[0], 255) if displayImages: imp.show() IJ.run(imp, "Convert to Mask", "") IJ.run(imp, "Watershed", "") if not displayImages: imp.changes = False imp.close() # Counts and measures the area of particles and adds them to a table called areas. Also adds them to the ROI manager table = ResultsTable() roim = RoiManager(True) ParticleAnalyzer.setRoiManager(roim) pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 15, 9999999999999999, 0.2, 1.0) pa.setHideOutputImage(True) #imp = impM # imp.getProcessor().invert() pa.analyze(imp) areas = table.getColumn(0) # This loop goes through the remaining channels for the other markers, by replacing the ch00 at the end with its corresponding channel # It will save all the area fractions into a 2d array called areaFractionsArray areaFractionsArray = [None] * 5 for chan in channels: v, x = chan # Opens each image and thresholds imp = images[x] IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) ic = ImageConverter(imp) ic.convertToGray8() IJ.setThreshold(imp, lowerBounds[x], 255) if displayImages: imp.show() WaitForUserDialog("Title", "Adjust Threshold for Marker " + v).show() IJ.run(imp, "Convert to Mask", "") # Measures the area fraction of the new image for each ROI from the ROI manager. areaFractions = [] for roi in roim.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA_FRACTION) areaFractions.append(stats.areaFraction) # Saves the results in areaFractionArray areaFractionsArray[x] = areaFractions roim.close() for chan in channels: v, x = chan imp = images[x] imp.deleteRoi() roim = RoiManager(True) ParticleAnalyzer.setRoiManager(roim) pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 15, 9999999999999999, 0.2, 1.0) pa.analyze(imp) blobs = [] for roi in roim.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA) blobs.append(stats.area) blobsarea[x] = sum(blobs) blobsnuclei[x] = len(blobs) if not displayImages: imp.changes = False imp.close() roim.reset() roim.close() # Creates the summary dictionary which will correspond to a single row in the output csv, with each key being a column summary = {} summary['Image'] = filename summary['Directory'] = subFolder # Adds usual columns summary['size-average'] = 0 summary['#nuclei'] = 0 summary['all-negative'] = 0 summary['too-big-(>' + str(tooBigThreshold) + ')'] = 0 summary['too-small-(<' + str(tooSmallThreshold) + ')'] = 0 # Creates the fieldnames variable needed to create the csv file at the end. fieldnames = [ 'Name', 'Directory', 'Image', 'size-average', 'too-big-(>' + str(tooBigThreshold) + ')', 'too-small-(<' + str(tooSmallThreshold) + ')', '#nuclei', 'all-negative' ] # Adds the columns for each individual marker (ignoring Dapi since it was used to count nuclei) summary["organoid-area"] = bigAreas[x] fieldnames.append("organoid-area") for chan in channels: v, x = chan summary[v + "-positive"] = 0 fieldnames.append(v + "-positive") summary[v + "-intensity"] = intensities[x] fieldnames.append(v + "-intensity") summary[v + "-blobsarea"] = blobsarea[x] fieldnames.append(v + "-blobsarea") summary[v + "-blobsnuclei"] = blobsnuclei[x] fieldnames.append(v + "-blobsnuclei") # Adds the column for colocalization between first and second marker if len(channels) > 2: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-positive') # Adds the columns for colocalization between all three markers if len(channels) > 3: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[2][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive') # Loops through each particle and adds it to each field that it is True for. areaCounter = 0 for z, area in enumerate(areas): log.write(str(area)) log.write("\n") if area > tooBigThreshold: summary['too-big-(>' + str(tooBigThreshold) + ')'] += 1 elif area < tooSmallThreshold: summary['too-small-(<' + str(tooSmallThreshold) + ')'] += 1 else: summary['#nuclei'] += 1 areaCounter += area temp = 0 for chan in channels: v, x = chan if areaFractionsArray[x][z] > areaFractionThreshold[ 0]: #theres an error here im not sure why. i remember fixing it before summary[chan[0] + '-positive'] += 1 if x != 0: temp += 1 if temp == 0: summary['all-negative'] += 1 if len(channels) > 2: if areaFractionsArray[1][z] > areaFractionThreshold[1]: if areaFractionsArray[2][z] > areaFractionThreshold[2]: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] += 1 if len(channels) > 3: if areaFractionsArray[1][z] > areaFractionThreshold[1]: if areaFractionsArray[3][z] > areaFractionThreshold[3]: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[2][z] > areaFractionThreshold[2]: if areaFractionsArray[3][z] > areaFractionThreshold[3]: summary[channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[1][z] > areaFractionThreshold[1]: summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 # Calculate the average of the particles sizes if float(summary['#nuclei']) > 0: summary['size-average'] = round(areaCounter / summary['#nuclei'], 2) # Opens and appends one line on the final csv file for the subfolder (remember that this is still inside the loop that goes through each image) with open(outputDirectory + "/" + outputName + ".csv", 'a') as csvfile: writer = csv.DictWriter(csvfile, fieldnames=fieldnames, extrasaction='ignore', lineterminator='\n') if os.path.getsize(outputDirectory + "/" + outputName + ".csv") < 1: writer.writeheader() writer.writerow(summary)
def duty_cycle(i, horizontal): IJ.open(i) IJ.run("Enhance Contrast...", "saturated=0.3 equalize") IJ.run("Smooth", "") 'IJ.run("Anisotropic Diffusion 2D", "number=20 smoothings=1 keep=20 a1=0.50 a2=0.90 dt=20 edge=5") # use instead of smooth for better results, slower imp = IJ.getImage() ImageConverter(imp).convertToGray8() file_base = str(imp.title) # convert name into string file_base = file_base.split('.', 1)[0] # remove all characters including and after . sample_id = file_base.split('_', 1)[0] height = imp.height width = imp.width IJ.run(imp, "Set Scale...", "distance=5000 known=1 pixel=1 unit=cm") IJ.setTool("line") for scan in range(1, num_scans): row_count = 0 data=[] data2=[] last = 0 filename = file_base + "_" + str(scan) if not horizontal: IJ.makeLine(0, scan*height/num_scans, width, scan*height/num_scans) # horizontal line to measure vertical grating profile else: IJ.makeLine(width*scan/num_scans, 9*height/10, width*scan/num_scans, 0) # vertical line to measure horizontal grating profile IJ.run(imp, "Plot Profile", "") imp_plot = IJ.getImage() IJ.run(imp, "Find Peaks", setting) # nw07 params: min._peak_amplitude=60 min._peak_distance=0 min._value=100 max._value=0 exclude list IJ.saveAs("Results", csvpath + filename + "_raw.csv") imp_plot.close() imp_plot = IJ.getImage() IJ.saveAs("Png", csvpath + "Peaks in Plot of " + filename + ".png") imp_plot.close() IJ.selectWindow(filename + "_raw.csv") IJ.run("Close") with open(csvpath + filename + "_raw.csv", "rb") as fin, open(csvpath + filename + "_peaks.csv", "wb") as fout: writer = csv.writer(fout) for row in csv.reader(fin): if not row[2] == '': writer.writerow(row) with open(csvpath + filename + "_peaks.csv", "rb") as File: reader = csv.reader(File) for row in reader: row_count += 1 if row_count == 1: continue data.append(tuple(row)) # Append all non-header rows into a list of data as a tuple of cells for row in sort_table(data, 2): data2.append(tuple(row)) if len(data2) < 3: IJ.log(filename + " no peaks detected, skipping...") continue else: peaks = len(data2) last = data2[0] last = last[2] row_count = 0 diff = 0 colG = [] blank = "" duty = zip(*data2) for row in data2: row_count += 1 if row_count == 1: continue else: print row[2] print last diff = float(row[2]) - float(last) colG.append(diff) last = row[2] a, b = colG[::2], colG[1::2] avga = sum(a)/len(a) avgb = sum(b)/len(b) a_len_dev = len(a) - 1 b_len_dev = len(b) - 1 if b_len_dev > 1: a_stdev = sqrt(sum((x - avga)**2 for x in a) / a_len_dev) b_stdev = sqrt(sum((x - avgb)**2 for x in b) / b_len_dev) else: a_stdev = 1 b_stdev = 1 duty_cyc = avga/(avga+avgb) perc = duty_cyc*100 invperc = 100 - perc inv_duty = 1 - duty_cyc duty_max = max(duty_cyc, inv_duty) duty_min = min(duty_cyc, inv_duty) percs = round(perc) percs = int(percs) percs = str(percs) invpercs = round(invperc) invpercs = int(invpercs) invpercs = str(invpercs) colG.insert(0, blank) a.insert(0, blank) b.insert(0, blank) b.insert(1, blank) i = 0 while i < len(a): i += 2 a.insert(i, blank) i = 1 while i < len(b): i += 2 b.insert(i, blank) duty.append(colG) duty.append(a) duty.append(b) duty = zip(*duty) result = [sample_id, file_base, scan, duty_cyc, inv_duty, a_stdev, b_stdev, peaks, duty_max, duty_min] header = ["X0", "Y0", "X1", "Y1", "X2", "Y2", "diff", "a", "b"] results.append(result) with open(csvpath + filename + "_duty.csv", 'wb') as myfile: wr = csv.writer(myfile, delimiter=',', quotechar='|', quoting=csv.QUOTE_MINIMAL) wr.writerow(header) wr.writerows(duty) print(filename + " duty cycle is " + percs + "/" + invpercs + "%.") IJ.log(filename + " duty cycle is " + percs + "/" + invpercs + "% (" + str(peaks) + " peaks found)") with open(csvpath + "results.csv", 'wb') as myfile: wr = csv.writer(myfile, delimiter=',', quotechar='|', quoting=csv.QUOTE_MINIMAL) wr.writerows(results) # Write the result data from all images into a single csv file
def loadTif(self, allowOverwrite=1): if self.header['b_sequence'] == 'Linescan': bPrintLog('Skipping: bPrairie2tif does not support Linescan, email bob and have him implement this', 3) return 0 width = None height = None #ip_ch1 = [] # a list of images as a list of 'image processor' #ip_ch2 = [] #ip_ch3 = [] bPrintLog('Loading ' + str(self.header['b_numSlices']) + ' Files ...', 3) numFiles = 0 infoStr = '' # sort individual .tif files into ch1 and ch2 for filename in os.listdir(self.srcFolder): if filename.endswith(".tif") and not filename.startswith('.'): # bPrintLog('opening:' + filename, 3) try: imp = IJ.openImage(self.srcFolder + filename) if imp is None: bPrintLog("ERROR: prairie2stack() could not open image from file:" + self.srcFolder + filename) continue isch1 = '_Ch1_' in filename isch2 = '_Ch2_' in filename isch3 = '_Ch3_' in filename if numFiles == 0: # don;t do this, header is to big to keep with output .tif #infoStr = imp.getProperty("Info") #get all tags, this is usefless infoStr += '\n' + self.infoStr0 # when appending, '\n' (EOL) is important because header does NOT end in EOL width = imp.width height = imp.height #stack = imp.getImageStack() #cp = stack.getProcessor(1) # assume 1 channel if isch1: #ip_ch1.append(cp) if self.imp_ch1 is None: self.imp_ch1 = imp else: self.imp_ch1 = Concatenator.run(self.imp_ch1, imp) elif isch2: #ip_ch2.append(cp) if self.imp_ch2 is None: self.imp_ch2 = imp else: self.imp_ch2 = Concatenator.run(self.imp_ch2, imp) elif isch3: #ip_ch3.append(cp) if self.imp_ch3 is None: self.imp_ch3 = imp else: self.imp_ch3 = Concatenator.run(self.imp_ch3, imp) else: bPrintLog('ERROR: did not find channel name in file:' + filename) numFiles += 1 except: continue #bPrintLog("exception error: prairie2stack() could not open image from file:" + self.srcFolder + filename) bPrintLog('Loaded ' + str(numFiles) + ' files ...', 3) ''' bPrintLog('ch1 has ' + str(len(ip_ch1)) + ' slices', 4) bPrintLog('ch2 has ' + str(len(ip_ch2)) + ' slices', 4) bPrintLog('ch3 has ' + str(len(ip_ch3)) + ' slices', 4) ''' #20170314, need to rewrite this to loop through channels (lots of repeated code here if self.imp_ch1 is not None: self.imp_ch1.setProperty("Info", infoStr); if self.imp_ch2 is not None: self.imp_ch2.setProperty("Info", infoStr); if self.imp_ch3 is not None: self.imp_ch3.setProperty("Info", infoStr); #ch1 #if ip_ch1: if self.imp_ch1: # bPrintLog('ch1 has ' + str(self.imp_ch1.getNSlices()) + ' slices', 4) ''' stack_ch1 = ImageStack(width, height) for fp in ip_ch1: stack_ch1.addSlice(fp) self.imp_ch1 = ImagePlus('xxx', stack_ch1) self.imp_ch1.setProperty("Info", infoStr); ''' # median filter if globalOptions['medianFilter']>0: bPrintLog('ch1: Running median filter: ' + str(globalOptions['medianFilter']), 4) medianArgs = 'radius=' + str(globalOptions['medianFilter']) + ' stack' IJ.run(self.imp_ch1, "Median...", medianArgs); infoStr += 'bMedianFilter=' + str(globalOptions['medianFilter']) + '\n' self.imp_ch1.setProperty("Info", infoStr) if globalOptions['convertToEightBit']: bPrintLog('converting to 8-bit by dividing image down and then convert to 8-bit with ImageConverter.setDoScaling(False)', 4) bitDepth = 2^13 divideBy = bitDepth / 2^8 # divide the 13 bit image down to 8 bit #run("Divide...", "value=32 stack"); bPrintLog('divideBy:' + str(divideBy), 4) divideArgs = 'value=' + str(divideBy) + ' stack' IJ.run(self.imp_ch1, "Divide...", divideArgs); # convert to 8-bit will automatically scale, to turn this off use # eval("script", "ImageConverter.setDoScaling(false)"); ImageConverter.setDoScaling(False) # run("8-bit"); bPrintLog('converting to 8-bit with setDoScaling False', 4) IJ.run(self.imp_ch1, "8-bit", ''); # print stats including intensity for the stack we just made # Returns the dimensions of this image (width, height, nChannels, nSlices, nFrames) as a 5 element int array. d = self.imp_ch1.getDimensions() # width, height, nChannels, nSlices, nFrames stats = self.imp_ch1.getStatistics() # stats.min, stats.max bPrintLog('ch1 dimensions w:' + str(d[0]) + ' h:' + str(d[1]) + ' channels:' + str(d[2]) + ' slices:' + str(d[3]) + ' frames:' + str(d[4]), 4) bPrintLog('ch1 intensity min:' + str(stats.min) + ' max:' + str(stats.max), 4) # set the voxel size so opening in Fiji will report correct bit depth # run("Properties...", "channels=1 slices=300 frames=1 unit=um pixel_width=.2 pixel_height=.3 voxel_depth=.4"); #ch2 #if ip_ch2: if self.imp_ch2: # bPrintLog('ch2 has ' + str(self.imp_ch2.getNSlices()) + ' slices', 4) ''' stack_ch2 = ImageStack(width, height) for fp in ip_ch2: stack_ch2.addSlice(fp) self.imp_ch2 = ImagePlus('xxx', stack_ch2) self.imp_ch2.setProperty("Info", infoStr); ''' # median filter if globalOptions['medianFilter']>0: bPrintLog('ch2: Running median filter: ' + str(globalOptions['medianFilter']), 4) medianArgs = 'radius=' + str(globalOptions['medianFilter']) + ' stack' IJ.run(self.imp_ch2, "Median...", medianArgs); infoStr += 'bMedianFilter=' + str(globalOptions['medianFilter']) + '\n' self.imp_ch2.setProperty("Info", infoStr) if globalOptions['convertToEightBit']: bPrintLog('converting to 8-bit by dividing image down and then convert to 8-bit with ImageConverter.setDoScaling(False)', 4) bitDepth = 2^13 divideBy = bitDepth / 2^8 # divide the 13 bit image down to 8 bit #run("Divide...", "value=32 stack"); bPrintLog('divideBy:' + str(divideBy), 4) divideArgs = 'value=' + str(divideBy) + ' stack' IJ.run(self.imp_ch2, "Divide...", divideArgs); # convert to 8-bit will automatically scale, to turn this off use # eval("script", "ImageConverter.setDoScaling(false)"); ImageConverter.setDoScaling(False) # run("8-bit"); bPrintLog('converting to 8-bit with setDoScaling False', 4) IJ.run(self.imp_ch2, "8-bit", ''); # print stats including intensity for the stack we just made d = self.imp_ch2.getDimensions() # width, height, nChannels, nSlices, nFrames stats = self.imp_ch2.getStatistics() # stats.min, stats.max bPrintLog('ch2 dimensions w:' + str(d[0]) + ' h:' + str(d[1]) + ' channels:' + str(d[2]) + ' slices:' + str(d[3]) + ' frames:' + str(d[4]), 4) bPrintLog('ch2 intensity min:' + str(stats.min) + ' max:' + str(stats.max), 4) #ch2 #if ip_ch3: if self.imp_ch3: # bPrintLog('ch1 has ' + str(self.imp_ch3.getNSlices()) + ' slices', 4) ''' stack_ch3 = ImageStack(width, height) for fp in ip_ch3: stack_ch3.addSlice(fp) self.imp_ch3 = ImagePlus('xxx', stack_ch3) self.imp_ch3.setProperty("Info", infoStr); ''' # median filter if globalOptions['medianFilter']>0: bPrintLog('ch3: Running median filter: ' + str(globalOptions['medianFilter']), 4) medianArgs = 'radius=' + str(globalOptions['medianFilter']) + ' stack' IJ.run(self.imp_ch3, "Median...", medianArgs); infoStr += 'bMedianFilter=' + str(globalOptions['medianFilter']) + '\n' self.imp_ch3.setProperty("Info", infoStr) if globalOptions['convertToEightBit']: bPrintLog('converting to 8-bit by dividing image down and then convert to 8-bit with ImageConverter.setDoScaling(False)', 4) bitDepth = 2^13 divideBy = bitDepth / 2^8 # divide the 13 bit image down to 8 bit #run("Divide...", "value=32 stack"); bPrintLog('divideBy:' + str(divideBy), 4) divideArgs = 'value=' + str(divideBy) + ' stack' IJ.run(self.imp_ch3, "Divide...", divideArgs); # convert to 8-bit will automatically scale, to turn this off use # eval("script", "ImageConverter.setDoScaling(false)"); ImageConverter.setDoScaling(False) # run("8-bit"); bPrintLog('converting to 8-bit with setDoScaling False', 4) IJ.run(self.imp_ch3, "8-bit", ''); # print stats including intensity for the stack we just made d = self.imp_ch3.getDimensions() # width, height, nChannels, nSlices, nFrames stats = self.imp_ch3.getStatistics() # stats.min, stats.max bPrintLog('ch3 dimensions w:' + str(d[0]) + ' h:' + str(d[1]) + ' channels:' + str(d[2]) + ' slices:' + str(d[3]) + ' frames:' + str(d[4]), 4) bPrintLog('ch3 intensity min:' + str(stats.min) + ' max:' + str(stats.max), 4) return 1
image.close() #image = ImagePlus("test", twochannel_stack) #fs = FileSaver(image) #filepath = directory + "/" + filename + "_twochannel.tif" #fs.saveAsTiff(filepath) image_dapi = ImagePlus("dapi stack", dapi_stack) image_dapi.show() image_green = ImagePlus("green stack", green_stack) image_green.show() image = ImagePlus("two channel stack", twochannel_stack) image.show() if auto_thresh: con = ImageConverter(image) con.convertToGray8() IJ.run(image, "Auto Local Threshold", "method=Bernsen radius=15 parameter_1=0 parameter_2=0 white stack") #image = CompositeImage(image_two) #image = IJ.getImage() z_slices = image.getDimensions()[3] / 2 print("order=xyczt(default) channels=2 slices="+ str(z_slices) + " frames=1 display=Color", image.getDimensions()) image_two = HyperStackConverter.toHyperStack(image,2,z_slices,1) image = CompositeImage(image_two) image.show() rt = run_comdet(image) rt.save(directory+"/"+filename+"_results.csv" ) image = IJ.getImage()
# root = '/data/hanslovskyp/crack_from_john/substacks/03/' # root = '/data/hanslovskyp/davi_toy_set/' # root = '/data/hanslovskyp/davi_toy_set/substacks/remove/01/' # root = '/data/hanslovskyp/davi_toy_set/substacks/replace_by_average/01/' # root = '/data/hanslovskyp/davi_toy_set/substacks/shuffle/03/' # root = '/data/hanslovskyp/jain-nobackup/234/' # root = '/data/hanslovskyp/jain-nobackup/234_data_downscaled/crop-150x150+75+175/' # root = '/data/hanslovskyp/jain-nobackup/234/substacks/crop-150x150+75+175/' # root = '/data/hanslovskyp/forPhilipp/substacks/04/' # root = '/data/hanslovskyp/forPhilipp/substacks/05/' root = '/data/hanslovskyp/jain-nobackup/234_data_downscaled/crop-100x100+100+200/' IJ.run("Image Sequence...", "open=%s/data number=%d sort" % ( root.rstrip(), nImages ) ); # imgSource = FolderOpener().open( '%s/data' % root.rstrip('/') ) imgSource = IJ.getImage() # imgSource.show() conv = ImageConverter( imgSource ) conv.convertToGray32() stackSource = imgSource.getStack() nThreads = 50 scale = 1.0 scaleZBy = 1.0 # 5.0 # stackMin, stackMax = ( None, 300 ) # xyScale = 0.25 # fibsem (crack from john) ~> 0.25 # xyScale = 0.1 # fibsem (crop from john) ~> 0.1? # boergens nImages = stackSource.getSize() xyScale = 1.0 doXYScale = False matrixSize = nImages matrixScale = 1 serializeCorrelations = False deserializeCorrelations = not serializeCorrelations
def getGrayScaleImage(currIP, c, chanName, cfg): if (cfg.hasValue(ELMConfig.upperLeftExclusionX)): ulExclusionX = cfg.getValue(ELMConfig.upperLeftExclusionX) else: ulExclusionX = 0 if (cfg.hasValue(ELMConfig.upperLeftExclusionY)): ulExclusionY = cfg.getValue(ELMConfig.upperLeftExclusionY) else: ulExclusionY = 0 if (cfg.hasValue(ELMConfig.lowerRightExclusionX)): lrExclusionX = cfg.getValue(ELMConfig.lowerRightExclusionX) else: lrExclusionX = currIP.getWidth() if (cfg.hasValue(ELMConfig.lowerRightExclusionY)): lrExclusionY = cfg.getValue(ELMConfig.lowerRightExclusionY) else: lrExclusionY = currIP.getHeight() imgType = currIP.getType() if (chanName in cfg.getValue( ELMConfig.chansToSkip)): # Don't process skip channels currIP.close() return None elif imgType == ImagePlus.COLOR_RGB or imgType == ImagePlus.COLOR_256: if (chanName == ELMConfig.BRIGHTFIELD): toGray = ImageConverter(currIP) toGray.convertToGray8() elif (chanName == ELMConfig.BLUE) \ or (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.RED) \ or (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.GREEN): # chanIdx = 2 if (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.RED): chanIdx = 0 elif (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.GREEN): chanIdx = 1 imgChanns = ChannelSplitter.split(currIP) currIP.close() currIP = imgChanns[chanIdx] # Clear the Exclusion zone, so it doesn't mess with thresholding imgProc = currIP.getProcessor() imgProc.setColor(Color(0, 0, 0)) imgProc.fillRect(lrExclusionX, lrExclusionY, currIP.getWidth(), currIP.getHeight()) imgProc.fillRect(0, 0, ulExclusionX, ulExclusionY) elif (chanName == ELMConfig.YELLOW): # Clear the Exclusion zone, so it doesn't mess with thresholding imgProc = currIP.getProcessor() imgProc.setColor(Color(0, 0, 0)) imgProc.fillRect(lrExclusionX, lrExclusionY, currIP.getWidth(), currIP.getHeight()) imgProc.fillRect(0, 0, ulExclusionX, ulExclusionY) # Create a new image that consists of the average of the red & green channels title = currIP.getTitle() width = currIP.getWidth() height = currIP.getHeight() newPix = ByteProcessor(width, height) for x in range(0, width): for y in range(0, height): currPix = currIP.getPixel(x, y) newPix.putPixel(x, y, (currPix[0] + currPix[1]) / 2) currIP.close() currIP = ImagePlus(title, newPix) else: print "ERROR: Unrecognized channel name! Name: " + chanName currIP.close() return None elif imgType == ImagePlus.GRAY16 or imgType == ImagePlus.GRAY32 or imgType == ImagePlus.GRAY8: if not imgType == ImagePlus.GRAY8: toGray = ImageConverter(currIP) toGray.convertToGray8() else: print "ERROR: Unrecognized channel name & image type! Channel: " + chanName + ", imgType: " + str( imgType) currIP.close() return None return currIP
def getThresholdedMask(currIP, c, z, t, chanName, cfg, wellPath, dbgOutDesc): if (cfg.hasValue(ELMConfig.upperLeftExclusionX)): ulExclusionX = cfg.getValue(ELMConfig.upperLeftExclusionX) else: ulExclusionX = 0 if (cfg.hasValue(ELMConfig.upperLeftExclusionY)): ulExclusionY = cfg.getValue(ELMConfig.upperLeftExclusionY) else: ulExclusionY = 0 if (cfg.hasValue(ELMConfig.lowerRightExclusionX)): lrExclusionX = cfg.getValue(ELMConfig.lowerRightExclusionX) else: lrExclusionX = currIP.getWidth() if (cfg.hasValue(ELMConfig.lowerRightExclusionY)): lrExclusionY = cfg.getValue(ELMConfig.lowerRightExclusionY) else: lrExclusionY = currIP.getHeight() imgType = currIP.getType() if (chanName in cfg.getValue( ELMConfig.chansToSkip)): # Don't process skip channels currIP.close() return None elif imgType == ImagePlus.COLOR_RGB or imgType == ImagePlus.COLOR_256: if (chanName == ELMConfig.BRIGHTFIELD): toGray = ImageConverter(currIP) toGray.convertToGray8() if cfg.params[ELMConfig.imgType] == "png": darkBackground = True else: darkBackground = False elif (chanName == ELMConfig.BLUE) \ or (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.RED) \ or (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.GREEN): # chanIdx = 2 if (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.RED): chanIdx = 0 elif (cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.GREEN): chanIdx = 1 imgChanns = ChannelSplitter.split(currIP) currIP.close() currIP = imgChanns[chanIdx] # Clear the Exclusion zone, so it doesn't mess with thresholding imgProc = currIP.getProcessor() imgProc.setColor(Color(0, 0, 0)) imgProc.fillRect(lrExclusionX, lrExclusionY, currIP.getWidth(), currIP.getHeight()) imgProc.fillRect(0, 0, ulExclusionX, ulExclusionY) darkBackground = True elif (chanName == ELMConfig.YELLOW): # Clear the Exclusion zone, so it doesn't mess with thresholding imgProc = currIP.getProcessor() imgProc.setColor(Color(0, 0, 0)) imgProc.fillRect(lrExclusionX, lrExclusionY, currIP.getWidth(), currIP.getHeight()) imgProc.fillRect(0, 0, ulExclusionX, ulExclusionY) # Create a new image that consists of the average of the red & green channels title = currIP.getTitle() width = currIP.getWidth() height = currIP.getHeight() newPix = ByteProcessor(width, height) for x in range(0, width): for y in range(0, height): currPix = currIP.getPixel(x, y) newPix.putPixel(x, y, (currPix[0] + currPix[1]) / 2) currIP.close() currIP = ImagePlus(title, newPix) darkBackground = True else: print "ERROR: Unrecognized channel name! Name: " + chanName currIP.close() return None elif imgType == ImagePlus.GRAY16 or imgType == ImagePlus.GRAY32 or imgType == ImagePlus.GRAY8: if (chanName == ELMConfig.BRIGHTFIELD): if cfg.params[ELMConfig.imgType] == "png": darkBackground = True else: darkBackground = False else: darkBackground = True if not imgType == ImagePlus.GRAY8: toGray = ImageConverter(currIP) toGray.convertToGray8() else: print "ERROR: Unrecognized channel name & image type! Channel: " + chanName + ", imgType: " + str( imgType) currIP.close() return None WindowManager.setTempCurrentImage(currIP) if cfg.getValue(ELMConfig.debugOutput): IJ.saveAs('png', os.path.join(wellPath, "Processing_" + dbgOutDesc + ".png")) upperThreshImg = currIP.duplicate() # If threshold value is set, use it if (cfg.hasValue(ELMConfig.imageThreshold)): thresh = cfg.getValue(ELMConfig.imageThreshold) if (darkBackground): currIP.getProcessor().setThreshold(thresh, 255, ImageProcessor.NO_LUT_UPDATE) else: currIP.getProcessor().setThreshold(0, thresh, ImageProcessor.NO_LUT_UPDATE) else: # Otherise, automatically compute threshold threshMethod = "Default" if cfg.hasValue(ELMConfig.thresholdMethod): threshMethod = cfg.getValue(ELMConfig.thresholdMethod) currIP.getProcessor().setAutoThreshold(threshMethod, darkBackground, ImageProcessor.NO_LUT_UPDATE) threshRange = currIP.getProcessor().getMaxThreshold( ) - currIP.getProcessor().getMinThreshold() #print "\t\tZ = " + str(z) + ", T = " + str(t) + ", chan " + chanName + ": Using default threshold of minThresh: " + str(currIP.getProcessor().getMinThreshold()) + ", maxThresh: " + str(currIP.getProcessor().getMaxThreshold()) if currIP.getType() != ImagePlus.GRAY8: print "\tChannel " + chanName + " is not GRAY8, instead type is %d" % currIP.getType( ) if threshRange > cfg.getValue(ELMConfig.maxThreshRange): if (cfg.hasValue(ELMConfig.defaultThreshold)): thresh = cfg.getValue(ELMConfig.defaultThreshold) print "\t\tZ = " + str(z) + ", T = " + str( t ) + ", chan " + chanName + ": Using default threshold of " + str( thresh) + ", minThresh: " + str(currIP.getProcessor( ).getMinThreshold()) + ", maxThresh: " + str( currIP.getProcessor().getMaxThreshold()) if (darkBackground): currIP.getProcessor().setThreshold( thresh, 255, ImageProcessor.NO_LUT_UPDATE) else: currIP.getProcessor().setThreshold( 0, thresh, ImageProcessor.NO_LUT_UPDATE) else: print "\t\tZ = " + str(z) + ", T = " + str( t ) + ", chan " + chanName + ": Ignored Objects due to threshold range! minThresh: " + str( currIP.getProcessor().getMinThreshold( )) + ", maxThresh: " + str( currIP.getProcessor().getMaxThreshold()) currIP.close() return None IJ.run(currIP, "Convert to Mask", "") # Clear out exclusion zones imgProc = currIP.getProcessor() imgProc.fillRect(lrExclusionX, lrExclusionY, currIP.getWidth(), currIP.getHeight()) imgProc.fillRect(0, 0, ulExclusionX, ulExclusionY) IJ.run(currIP, "Close-", "") # Brightfield has an additional thresholding step if cfg.getValue(ELMConfig.chanLabel)[c] == ELMConfig.BRIGHTFIELD: if cfg.getValue(ELMConfig.debugOutput): IJ.saveAs( 'png', os.path.join(wellPath, "OrigMask_" + dbgOutDesc + ".png")) upperThresh = 255 * 0.95 upperThreshImg.getProcessor().setThreshold( upperThresh, 255, ImageProcessor.NO_LUT_UPDATE) IJ.run(upperThreshImg, "Convert to Mask", "") IJ.run(upperThreshImg, "Close-", "") if cfg.getValue(ELMConfig.debugOutput): WindowManager.setTempCurrentImage(upperThreshImg) IJ.saveAs( 'png', os.path.join(wellPath, "UpperThreshMask_" + dbgOutDesc + ".png")) ic = ImageCalculator() compositeMask = ic.run("OR create", currIP, upperThreshImg) IJ.run(compositeMask, "Close-", "") currIP.close() currIP = compositeMask WindowManager.setTempCurrentImage(currIP) if cfg.getValue(ELMConfig.debugOutput): WindowManager.setTempCurrentImage(currIP) IJ.saveAs('png', os.path.join(wellPath, "Binary_" + dbgOutDesc + ".png")) upperThreshImg.close() return currIP
for channel in range(1, (number_of_channels_in_mouse + 1)): channel_files = getChannelFiles(MouseIDFiles, channel) # get the full path chf_fpaths = [path.join(In_dir, x) for x in channel_files] # get the minimum and maximum pixel value min_pixval, max_pixval = get_enhance_bounds( chf_fpaths, low_theshold, high_threshold) IJ.log("Found pixel bounds " + str(min_pixval) + " and " + str(max_pixval) + " for channel " + str(channel)) counter = 1 for chfile in chf_fpaths: # open file ch_img = Opener().openImage(chfile) ch_tit = ch_img.getTitle() # adjust contrast ch_img.getProcessor().setMinAndMax(min_pixval, max_pixval) # convert to 8-bit (which also applies the contrast) ImageConverter(ch_img).convertToGray8() # save IJ.saveAsTiff(ch_img, path.join(Out_dir, ch_tit)) # close and flush ch_img.close() ch_img.flush() print("Image " + str(counter) + " of " + str(len(chf_fpaths)) + " processed") counter += 1 IJ.log('Mouse ' + MouseID + ' processed') print("DONE, find your results in " + Out_dir)
for al in als: al.setProperty("label", None) al.setVisible(False, True) for i in range(1, Label_Max + 1): NN = "N" + str(i) bFound = False for al in als: if NN == al.title: bFound = True al.setProperty("label", str(i)) break if (not bFound): print(NN) print("miss") File(savDir).mkdirs() for al in als: if al.title.startswith('N'): print("processing: " + al.title) al.setVisible(True, True) al.exportAsLabels([al], None, 1, 0, int(ls.getDepth()), True, False, False) al.setVisible(False, True) imp = WM.getImage("Labels") ImageConverter(imp).convertToGray16() FileSaver(imp).saveAsTiff(savDir + al.title + ".tif") imp.close() print("done")
subfolders = [""] for subfolder in subfolders: #Opens each image for filename in os.listdir(inputDirectory + subfolder): imp = IJ.openImage(inputDirectory + subfolder + '/' + filename) if imp: # 10X objective IJ.run(imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=" +str(pix_width)+ " pixel_height=" +str(pix_height)+" voxel_depth=25400.0508001") # Change to a GUI option later? # Threshold, fills hole and watershed ic = ImageConverter(imp); ic.convertToGray8(); IJ.setAutoThreshold(imp, "Default dark") if thresholdMode: imp.show() IJ.run("Threshold...") WaitForUserDialog("Title", "Adjust threshold").show() IJ.run(imp, "Convert to Mask", "") if not inverted: IJ.run(imp, "Invert", "") IJ.run(imp, "Fill Holes", "") if watershedMode:
def process(subDir, subsubDir, outputDirectory, filename): subFolder = subDir + "/" + subsubDir # Opens the d0 image and sets default properties imp = IJ.openImage(inputDirectory + subFolder + '/' + filename) IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) # Sets the threshold and watersheds. for more details on image processing, see https://imagej.nih.gov/ij/developer/api/ij/process/ImageProcessor.html ic = ImageConverter(imp) ic.convertToGray8() imp.updateAndDraw() dup = imp.duplicate() IJ.run( dup, "Convolve...", "text1=[-1 -1 -1 -1 -1\n-1 -1 -1 -1 -1\n-1 -1 24 -1 -1\n-1 -1 -1 -1 -1\n-1 -1 -1 -1 -1\n] normalize" ) stats = dup.getStatistics(Measurements.MEAN | Measurements.MIN_MAX | Measurements.STD_DEV) dup.close() blurry = (stats.mean < 18 and stats.stdDev < 22) or stats.max < 250 IJ.setThreshold(imp, lowerBounds[0], 255) IJ.run(imp, "Convert to Mask", "") IJ.run(imp, "Watershed", "") if displayImages: imp.show() WaitForUserDialog("Title", "Look at image").show() # Counts and measures the area of particles and adds them to a table called areas. Also adds them to the ROI manager table = ResultsTable() roim = RoiManager(True) ParticleAnalyzer.setRoiManager(roim) pa = ParticleAnalyzer(ParticleAnalyzer.ADD_TO_MANAGER, Measurements.AREA, table, 15, 9999999999999999, 0.2, 1.0) pa.setHideOutputImage(True) pa.analyze(imp) if not displayImages: imp.changes = False imp.close() areas = table.getColumn(0) # This loop goes through the remaining channels for the other markers, by replacing the d0 at the end with its corresponding channel # It will save all the area fractions into a 2d array called areaFractionsArray areaFractionsArray = [] areaMeansArray = [] means = [] totalAreas = [] for chan in channels: v, x = chan # Opens each image and thresholds imp = IJ.openImage(inputDirectory + subFolder + '/' + filename.replace("d0.TIF", "d" + str(x) + ".TIF")) IJ.run( imp, "Properties...", "channels=1 slices=1 frames=1 unit=um pixel_width=0.8777017 pixel_height=0.8777017 voxel_depth=25400.0508001" ) ic = ImageConverter(imp) ic.convertToGray8() imp.updateAndDraw() stats = imp.getStatistics(Measurements.MEAN) means.append(stats.mean) areaMeans = [] for roi in roim.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.MEAN) areaMeans.append(stats.mean) IJ.setThreshold(imp, lowerBounds[x], 255) IJ.run(imp, "Convert to Mask", "") if displayImages: imp.show() WaitForUserDialog("Title", "Look at image").show() stats = imp.getStatistics(Measurements.AREA_FRACTION) totalAreas.append(stats.areaFraction) # Measures the area fraction of the new image for each ROI from the ROI manager. areaFractions = [] for roi in roim.getRoisAsArray(): imp.setRoi(roi) stats = imp.getStatistics(Measurements.AREA_FRACTION) areaFractions.append(stats.areaFraction) # Saves the results in areaFractionArray areaFractionsArray.append(areaFractions) areaMeansArray.append(sum(areaMeans) / len(areaMeans)) if not displayImages: imp.changes = False imp.close() roim.close() # Figures out what well the image is a part of ind = filename.index("p00_0_") row = filename[ind + 6:ind + 7] column = str(int(filename[ind + 7:ind + 9])) # Creates the summary dictionary which will correspond to a single row in the output csv, with each key being a column summary = {} # Finds the name of the well from the nameArray 2d array if row in nameArray: if column in nameArray[row]: summary['Name'] = nameArray[row][column] summary['Image'] = filename summary['Directory'] = subDir summary['SubDirectory'] = subsubDir summary['Row'] = row summary['Column'] = column # Adds usual columns summary['size-average'] = 0 summary['#nuclei'] = 0 summary['all-negative'] = 0 summary['too-big-(>' + str(tooBigThreshold) + ')'] = 0 summary['too-small-(<' + str(tooSmallThreshold) + ')'] = 0 summary['image-quality'] = blurry # Creates the fieldnames variable needed to create the csv file at the end. fieldnames = [ 'Name', 'Directory', 'SubDirectory', 'Image', 'Row', 'Column', 'size-average', 'image-quality', 'too-big-(>' + str(tooBigThreshold) + ')', 'too-small-(<' + str(tooSmallThreshold) + ')', '#nuclei', 'all-negative' ] # Adds the columns for each individual marker (ignoring Dapi since it was used to count nuclei) for chan in channels: v, x = chan summary[v + "-positive"] = 0 summary[v + "-intensity"] = means[x] summary[v + "-area"] = totalAreas[x] summary[v + "-intensity-in-nuclei"] = areaMeansArray[x] summary[v + "-area-fraction-in-nuclei"] = sum( areaFractionsArray[x]) / len(areaFractionsArray[x]) fieldnames.append(v + "-positive") fieldnames.append(v + "-intensity") fieldnames.append(v + "-area") fieldnames.append(v + "-intensity-in-nuclei") fieldnames.append(v + "-area-fraction-in-nuclei") # Adds the column for colocalization between first and second marker if len(channels) > 2: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-positive') # Adds the columns for colocalization between all three markers if len(channels) > 3: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] = 0 fieldnames.append(channels[1][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[2][0] + '-' + channels[3][0] + '-positive') fieldnames.append(channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive') # Loops through each particle and adds it to each field that it is True for. areaCounter = 0 if not (areas is None): for z, area in enumerate(areas): if not (area is None or summary is None): if area > tooBigThreshold: summary['too-big-(>' + str(tooBigThreshold) + ')'] += 1 elif area < tooSmallThreshold: summary['too-small-(<' + str(tooSmallThreshold) + ')'] += 1 else: summary['#nuclei'] += 1 areaCounter += area temp = 0 for y, chan in enumerate(channels): v, x = chan if areaFractionsArray[y][z] > areaFractionThreshold: summary[chan[0] + '-positive'] += 1 if x != 0: temp += 1 if temp == 0: summary['all-negative'] += 1 if len(channels) > 2: if areaFractionsArray[1][z] > areaFractionThreshold: if areaFractionsArray[2][z] > areaFractionThreshold: summary[channels[1][0] + '-' + channels[2][0] + '-positive'] += 1 if len(channels) > 3: if areaFractionsArray[1][z] > areaFractionThreshold: if areaFractionsArray[3][z] > areaFractionThreshold: summary[channels[1][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[2][z] > areaFractionThreshold: if areaFractionsArray[3][z] > areaFractionThreshold: summary[channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 if areaFractionsArray[1][ z] > areaFractionThreshold: summary[channels[1][0] + '-' + channels[2][0] + '-' + channels[3][0] + '-positive'] += 1 # Calculate the average of the particles sizes if float(summary['#nuclei']) > 0: summary['size-average'] = round(areaCounter / summary['#nuclei'], 2) # Opens and appends one line on the final csv file for the subfolder (remember that this is still inside the loop that goes through each image) with open(outputDirectory + "/" + outputName + ".csv", 'a') as csvfile: writer = csv.DictWriter(csvfile, fieldnames=fieldnames, extrasaction='ignore', lineterminator='\n') if os.path.getsize(outputDirectory + "/" + outputName + ".csv") < 1: writer.writeheader() writer.writerow(summary)
os.mkdir(transformation_outputdir) ############################################ preprocessing # open EM image EM = IJ.openImage(EMfilepath) # equalize histogramm IJ.run(EM, "Enhance Contrast...", "saturated=0.3 equalize") # resize EM image ip = EM.getProcessor() width = ip.getWidth() height = ip.getHeight() EM.setProcessor(EM.getTitle(), EM.getProcessor().resize(256, 256)) ImageConverter(EM).convertToGray8() # create stack z=2 EMstack = ImageStack(EM.getWidth(), EM.getHeight()) EMstack.addSlice(str(1), EM.getProcessor()) EMstack.addSlice(str(2), EM.getProcessor()) EM = ImagePlus(EM.getTitle(), EMstack) # save EM image saveEMfilepath = os.path.join(workdir, "EM.tif") fs = FileSaver(EM) fs.saveAsTiff(saveEMfilepath) print("(- )preprocessing done") ############################################ predict image
def natural_keys(text): return [ atoi(c) for c in re.split('(\d+)', text) ] os.chdir(mypath) alist = os.listdir(mypath) alist.sort(key=natural_keys) imp = IJ.openImage(mypath + alist[0]) signedpix = imp.getProcessor().toFloat(1, None) width=signedpix.getWidth() height=signedpix.getHeight() stack = ImageStack(width, height) i=0 for file in alist[:10]: print("Current File Being Processed is: " + file) imp = IJ.openImage(mypath + file) signedpix = imp.getProcessor().toFloat(1, None) stack.addSlice(str(i), signedpix) i = i + 1 imp = ImagePlus("", stack) ImageConverter(imp).convertToGray8() imp.show() IJ.runPlugIn("ij3d.ImageJ3DViewer", "")
dstpath = os.path.join(workDir, dstFile) # function: thresholding def threshold(p): if p > th[i][0] and p < th[i][1]: return p else: return 0.0 # open image (RGB) imp = IJ.openImage(srcpath) # convert ImageConverter(imp).convertToLab() ## imageProcessor ip = imp.getProcessor() # FloatProcessor by channel chpx = [] # channel pixels filtered = [] # filtered FloatProcessor for i in range(3): chpx.append(ip.toFloat(i, None).getPixels()) _filtered = [threshold(p) for p in chpx[i]] # filtered pixels filtered.append(FloatProcessor(ip.width, ip.height, _filtered, None)) # save each channels for i in range(3):
def main(): #print (sys.version_info) # debug #print(sys.path) # debug data_root = r'C:\Users\dougk\Desktop\test' # debug output_root = r'C:\Users\dougk\Desktop\test' #debug #default_directory = r'C:\\Users\\Doug\\Desktop\\test'; #data_root, output_root = file_location_chooser(default_directory); if (data_root is None) or (output_root is None): raise IOError("File location dialogs cancelled!") timestamp = datetime.strftime(datetime.now(), "%Y-%m-%d %H.%M.%S") output_path = os.path.join(output_root, (timestamp + " output")) for file_path in filterByFileType(os.listdir(data_root), '.tif'): subfolder_name = os.path.splitext(file_path)[0] output_subfolder = os.path.join(output_path, subfolder_name) print(output_subfolder) os.makedirs(output_subfolder) imps = bf.openImagePlus(os.path.join(data_root, file_path)) imp = imps[0] imp.show() h = imp.height w = imp.width slices = imp.getNSlices() channels = imp.getNChannels() frames = imp.getNFrames() # rotation step - since using multiples of 90, TransformJ.Turn is more efficient IJ.run("Enhance Contrast", "saturated=0.35") angleZ = 1 while ((angleZ % 90) > 0): gd = GenericDialog("Rotate?") gd.addMessage( "Define rotation angle - increments of 90. Apical at top") gd.addNumericField("Rotation angle", 0, 0) gd.showDialog() angleZ = int(gd.getNextNumber()) if (angleZ > 1): IJ.run("TransformJ Turn", "z-angle=" + str(angleZ) + " y-angle=0 x-angle=0") imp.close() imp = WindowManager.getCurrentImage() imp.setTitle(file_path) # trim time series IJ.run("Enhance Contrast", "saturated=0.35") imp.setDisplayMode(IJ.COLOR) WaitForUserDialog( "Scroll to the first frame of the period of interest and click OK" ).show() start_frame = imp.getT() WaitForUserDialog( "Scroll to the last frame of the period of interest and click OK" ).show() end_frame = imp.getT() trim_imp = Duplicator().run(imp, 1, channels, 1, slices, start_frame, end_frame) imp.close() trim_imp.show() dup_imp = Duplicator().run(trim_imp) # create images to process and find bounds for dup_imps = ChannelSplitter().split(dup_imp) myo_imp = dup_imps[1] mem_imp = dup_imps[0] FileSaver(myo_imp).saveAsTiffStack( os.path.join(output_subfolder, "myosin_channel.tif")) FileSaver(mem_imp).saveAsTiffStack( os.path.join(output_subfolder, "membrane_channel.tif")) # set basal bounds myo_imp.show() ImageConverter(myo_imp).convertToGray8() frames = myo_imp.getNFrames() gb = GaussianBlur() for fridx in range(0, frames): myo_imp.setSliceWithoutUpdate(fridx + 1) ip = myo_imp.getProcessor() gb.blurGaussian(ip, 5.0, 1.0, 0.02) # assymmetrical Gaussian IJ.run(myo_imp, "Convert to Mask", "method=Otsu background=Dark calculate") IJ.run("Despeckle", "stack") title = myo_imp.getTitle() # assume that first frame is good quality image... basal_edges = find_basal_edges(myo_imp) #myo_imp.hide() mem_imp.hide() # draw some edges for checking roim = RoiManager() xs = [x for x in range(1, trim_imp.getWidth() + 1)] trim_imp.show() for fridx in range(0, myo_imp.getNFrames()): trim_imp.setPosition(2, 1, fridx + 1) IJ.run("Enhance Contrast", "saturated=0.35") roi = PolygonRoi(xs, basal_edges[fridx], Roi.POLYLINE) trim_imp.setRoi(roi) roim.addRoi(roi)
def auto_threshold(imp_in, str_thresh, bScale=False): """ auto_threshold_otsu(imp_in, str_thresh="Otsu", bScale=True) Compute an autothreshold for an image. Adapted from http://wiki.cmci.info/documents/120206pyip_cooking/python_imagej_cookbook Parameters ---------- imp_in ImagePlus The image to threshold str_thresh String (Default: Default) The threshold: Otsu, Huang, IsoData, Intermodes, Li, MaxEntropy, Mean, MinError, Minimum, Moments, Percentile, RenyiEntropy, Shanbhag, Triangle, Yen, or Default bScale Boolean (Default: False) Return ------ imp_out ImagePlus The binary image thr_val integer The threshold value """ ti = imp_in.getShortTitle() imp = imp_in.duplicate() hist = imp.getProcessor().getHistogram() if (str_thresh == "Otsu"): lowTH = Auto_Threshold.Otsu(hist) elif (str_thresh == "Huang"): lowTH = Auto_Threshold.Huang(hist) elif (str_thresh == "Intermodes"): lowTH = Auto_Threshold.Intermodes(hist) elif (str_thresh == "IsoData"): lowTH = Auto_Threshold.IsoData(hist) elif (str_thresh == "Li"): lowTH = Auto_Threshold.Li(hist) elif (str_thresh == "MaxEntropy"): lowTH = Auto_Threshold.MaxEntropy(hist) elif (str_thresh == "Mean"): lowTH = Auto_Threshold.Mean(hist) elif (str_thresh == "MinError"): lowTH = Auto_Threshold.MinError(hist) elif (str_thresh == "Minimum"): lowTH = Auto_Threshold.Minimum(hist) elif (str_thresh == "Moments"): lowTH = Auto_Threshold.Moments(hist) elif (str_thresh == "Percentile"): lowTH = Auto_Threshold.Percentile(hist) elif (str_thresh == "RenyiEntropy"): lowTH = Auto_Threshold.RenyiEntropy(hist) elif (str_thresh == "Shanbhag"): lowTH = Auto_Threshold.Shanbhag(hist) elif (str_thresh == "Triangle"): lowTH = Auto_Threshold.Triangle(hist) elif (str_thresh == "Yen"): lowTH = Auto_Threshold.Yen(hist) else: lowTH = Auto_Threshold.Default(hist) imp.getProcessor().threshold(lowTH) imp.setDisplayRange(0, lowTH + 1) ImageConverter.setDoScaling(bScale) IJ.run(imp, "8-bit", "") imp.setDisplayRange(0, 255) imp.setTitle(ti + "-bin-" + str_thresh) return ([imp, lowTH])
def runOneTif(tifPath, dstTifPath): bPrintLog('=== runOneTif processing tif:' + tifPath, 3) bPrintLog('Loading file...', 3) imp = IJ.openImage(tifPath) if imp is None: bPrintLog('ERROR: could not open image from file:' + tifPath, 3) return 0 logStr = 'done loading file: ' + str(imp.width) + ' ' + str(imp.height) + ' ' + str(imp.getNSlices()) bPrintLog(logStr, 3) numSlices = imp.getNSlices() if numSlices>1: pass else: bPrintLog('ERROR: number of slices must be more than one, file: ' + tifPath) return 0 bPrintLog('numSlices: ' + str(numSlices), 3) infoStr = imp.getProperty("Info") #get all tags #print infoStr if infoStr is None: infoStr = '' infoStr += 'bAverageFrames=v0.1\n' imp.setProperty("Info", infoStr) imp.show() impWin = imp.getTitle() # # start body #infer type of file from # get the actual bit depth used (e.g. ScanImage is 11 bit, Prairie is 13 bit) header = bParseHeader(imp) b_sequence = '' if 'b_sequence' in header: b_sequence = str(header['b_sequence']) bPrintLog('b_sequence: ' + b_sequence, 3) madeAverage = 0 # if numSlices is not divisable by gNumToAverage then chop a few slices off bottom/end if b_sequence.startswith('TSeries'): if globalOptions['gNumToAverage'] > 1: numToRemove = numSlices % globalOptions['gNumToAverage'] if numToRemove > 0: bPrintLog('Removing bottom slices: ' + str(numToRemove), 3) # run("Slice Remover", "first=3 last=5 increment=1"); removeArgs = 'first=' + str(numSlices-numToRemove+1) + ' last=' + str(numSlices) + ' increment=1' IJ.run('Slice Remover', removeArgs) numSlices = imp.getNSlices() bPrintLog('numSlices: ' + str(numSlices), 3) #fix this: if stack is really short this will not be taken if (numSlices > globalOptions['gNumToAverage']): bPrintLog('Taking average of ' + str(globalOptions['gNumToAverage']) + ' slices from ' + str(numSlices), 3) stackRegParams = 'projection=[Average Intensity] group=' + str(globalOptions['gNumToAverage']) IJ.run('Grouped Z Project...', stackRegParams) # makes window AVG_ madeAverage = 1 avgWindow = 'AVG_' + impWin avgImp = WindowManager.getImage(avgWindow) avgSlices = avgImp.getNSlices() # Grouped Z PRoject swaps slices for frames? tmpSlices = avgImp.getNSlices() tmpFrames = avgImp.getNFrames() if tmpFrames > 1: newSlices = tmpFrames newFrames = tmpSlices nChannels = 1 bPrintLog('Swaping frames for slices after grouped z',3) bPrintLog('newSlices=' + str(newSlices) + ' newFrames='+str(newFrames), 4) avgImp.setDimensions(nChannels, newSlices, newFrames) infoStr += 'gNumToAverage=' + str(globalOptions['gNumToAverage']) + '\n' # I want to adjust the framePeriod, prairie would be 'b_framePeriod' avgImp.setProperty("Info", infoStr) else: avgImp = imp avgSlices = numSlices else: bPrintLog('Not taking average of sequence: ' + b_sequence,3) avgImp = imp avgSlices = numSlices if globalOptions['medianFilter']>0: bPrintLog('Running median filter: ' + str(globalOptions['medianFilter']), 3) medianArgs = 'radius=' + str(globalOptions['medianFilter']) + ' stack' IJ.run(avgImp, "Median...", medianArgs); infoStr += 'bMedianFilter=' + str(globalOptions['medianFilter']) + '\n' avgImp.setProperty("Info", infoStr) # convert to 8 bit # 1) read bit depth from header (e.g. 2^13) # 2) do math on image and convert to 8-bit # run("Divide...", "value=32 stack"); if globalOptions['gConvertToEightBit']: bPrintLog('converting to 8-bit by dividing image down and then convert to 8-bit with ImageConverter.setDoScaling(False)', 3) bitDepth = 2^13 divideBy = bitDepth / 2^8 # divide the 13 bit image down to 8 bit #run("Divide...", "value=32 stack"); bPrintLog('divideBy:' + str(divideBy), 3) divideArgs = 'value=' + str(divideBy) + ' stack' IJ.run(avgImp, "Divide...", divideArgs); # convert to 8-bit will automatically scale, to turn this off use # eval("script", "ImageConverter.setDoScaling(false)"); ImageConverter.setDoScaling(False) # run("8-bit"); bPrintLog('converting to 8-bit with setDoScaling False', 3) IJ.run(avgImp, "8-bit", ''); bPrintLog('Saving stack with ' + str(avgSlices) + ' slices:' + dstTifPath, 3) fs = FileSaver(avgImp) if avgSlices>1: fs.saveAsTiffStack(dstTifPath) else: fs.saveAsTiff(dstTifPath) if madeAverage: avgImp.changes = 0 avgImp.close() imp.changes = 0 imp.close() # end body # # why was this here #imp.changes = 0 #imp.close() return 1
def analyse(cwd, user, imagefolder, stats, experiments, multi, Rloc2, subfoldernames, names, statsfolderPath, cwdR): """ Main image analysis Gets user image analysis settings from the .csv file. If multiple experiments have been selected by the user (multi) each subfolder will be looped through. A nested loop will then interate through each .tif image and analyse. A .csv file will be produced for each folder analysed with the name of each image and its % neurite density and % myelination. A summary csv file will also be produced with the average % neurite density and % myelination for each subfolder. If statistical analysis has been selected (stats) then MyelinJ's Rscript will be run via the command line. If multple experiments is not selected then all of the images within the selected folder will be analysed together and no summary .csv will be produced. Independ of the analysis settings defined, a processed myelin channel image and a processed neurite channel image will be saved. The images can be any number of subdirectories (folders within folders). Parameters ---------- cwd : string Path for current working directory (location of MyelinJ folder in Fiji). user: string User name imagefolder: string Path to .tiff image folder(s) defined by user. stats: boolean Perform statistical analysing using R? experiments: 2D list of strings list of all the subfolders (experiments) that are in each experimental condition. multi: boolean Analyse multiple experiments? Rloc2: string file path to Rscript location subfoldernames: string name of each subfolder which denoates each individual experiment, if multple experiments are being analysed. names: array array of textfields for each experimental condition defined by user. User will enter the name of each experimental condition. statsfolderPath: string file path to the create statsfolder. cwdR: string file path to MyelinJstats.R """ # read settings from the user name CSV bg = False readsettings = [] imagenames = [] neuritedensity = [] myelinoverlay = [] myelinaverage2 = [] neuriteaverage2 = [] root = cwd filename = user fullpath = os.path.join(root, filename) f = open(fullpath, 'rb') readCSV = csv.reader(f) for row in readCSV: readsettings.append(row[0]) readsettings.append(row[1]) readsettings.append(row[2]) readsettings.append(row[3]) readsettings.append(row[4]) readsettings.append(row[5]) readsettings.append(row[6]) f.close() i = 0 for i in range(len(subfoldernames)): # if multiple experimental conditions has been selected each folder is treated as a # separate experiment and looped through separately otherwise all folders will be # treated as one experiment this only works for sub directories within the main folder. # Further folders will be ignored (each image can be in its own folder for example) if multi is True: # if multiple experiments are being analysed the file path is changed to the # current subfolder settings2 = os.path.join(imagefolder, subfoldernames[i]) if "Windows" in OS: settings2 = settings2 + "\\" elif "Mac" in OS: settings2 = settings2 + "/" else: settings2 = imagefolder # loop through all .tiff files in location for root, dirs, files in os.walk(settings2): for name in files: if name.endswith((".tif")): imagenames.append(os.path.join(name)) # open .tiff image, split channels and # convert to 8bit grey scale. imp = IJ.openImage(os.path.join(root, name)) g = int(readsettings[4]) r = int(readsettings[5]) imp = ChannelSplitter.split(imp) green = imp[g] red = imp[r] conv = ImageConverter(red) conv.convertToGray8() conv = ImageConverter(green) conv.convertToGray8() # thresholding to select cell bodies green2 = green.duplicate() if (readsettings[0] != "0") or (readsettings[1] != "0"): bg = True IJ.setAutoThreshold(green2, readsettings[2]) IJ.setRawThreshold(green2, int(readsettings[0]), int(readsettings[1]), None) Prefs.blackBackground = True IJ.run(green2, "Convert to Mask", "") IJ.run(green2, "Invert LUT", "") if readsettings[7] != "0": IJ.run(green2, "Make Binary", "") IJ.run( green2, "Remove Outliers...", "radius=" + readsettings[7] + " threshold=50 which=Dark") # CLAHE and background subtraction if readsettings[8] == "True": mpicbg.ij.clahe.Flat.getFastInstance().run( green, 127, 256, 3, None, False) if readsettings[9] == "True": calc = ImageCalculator() green = calc.run("Subtract create", green, red) elif readsettings[6] == "True": IJ.run(green, "Subtract Background...", "rolling=50") if readsettings[10] != "0": IJ.run(green, "Subtract...", "value=" + readsettings[10]) # run frangi vesselness pixelwidth = str(green.getCalibration().pixelWidth) IJ.run( green, "Frangi Vesselness (imglib, experimental)", "number=1 minimum=" + pixelwidth + " maximum=" + pixelwidth) green = IJ.getImage() # convert frangi vesselness image to 8bit grey scale conv = ImageConverter(green) conv.convertToGray8() IJ.run(green, "Convert to Mask", "") # remove cell bodies if bg is True: green = ImageCalculator().run("Subtract create", green, green2) # run grey scale morphology filter from MorpholibJ if readsettings[11] != "0": green = green.getProcessor() algo = BoxDiagonalOpeningQueue() algo.setConnectivity(4) result = algo.process(green, int(readsettings[11])) green = ImagePlus("result", result) IJ.run(green, "Invert LUT", "") if len(readsettings) > 14: # sparse neurite image analysis if readsettings[15] == "True": IJ.run( red, "Enhance Local Contrast (CLAHE)", "blocksize=127 histogram=256 maximum=3 mask=*None* fast_(less_accurate)" ) if readsettings[14] == "True": IJ.run(red, "Subtract Background...", "rolling=50") IJ.setAutoThreshold(red, readsettings[16]) IJ.setRawThreshold(red, int(readsettings[17]), int(readsettings[18]), None) IJ.run(red, "Convert to Mask", "") IJ.run(red, "Invert LUT", "") else: # dense neurite image analysis IJ.run( red, "Normalize Local Contrast", "block_radius_x=40 block_radius_y=40 standard_deviations=" + readsettings[12] + " center stretch") IJ.run(red, "Auto Threshold", "method=Default white") IJ.run(red, "Invert LUT", "") if readsettings[3] == "True": IJ.run(red, "Despeckle", "") IJ.saveAs(red, "Jpeg", settings2 + name + "neurites") # get number of neurite pixels # get number of neurite pixels statsneurite = red.getProcessor() statsneurite = statsneurite.getHistogram() neuritedensity.append(statsneurite[255]) IJ.saveAs(green, "Jpeg", settings2 + name + "myelinFinal") # get number of myelin pixels statsmyelin = green.getProcessor() statsmyelin = statsmyelin.getHistogram() myelinoverlay.append(statsmyelin[255]) closeallimages() # get pixel total of image whitepixels = (statsneurite[0]) blackpixels = (statsneurite[255]) totalpixels = whitepixels + blackpixels totalpixels = [totalpixels] * len(neuritedensity) # for each image calculate % myelination as number of myelin pixels # divided by the number of neurite pixels * 100 myelinoverlay = [ x1 / x2 * 100 for (x1, x2) in zip(myelinoverlay, neuritedensity) ] myelinaverage = sum(myelinoverlay) / len(myelinoverlay) myelinaverage2.append(myelinaverage) # for each image calculate % neurite density as neurite pixels divided # by the total number of pixels in the image * 100. neuritedensity = [ x1 / x2 * 100 for (x1, x2) in zip(neuritedensity, totalpixels) ] neuriteaverage = sum(neuritedensity) / len(neuritedensity) neuriteaverage2.append(neuriteaverage) name = "Image names" green = "% myelination" red = "% neurite density" imagenames = [name] + imagenames neuritedensity = [red] + neuritedensity myelinoverlay = [green] + myelinoverlay result = [] result.append(imagenames) result.append(neuritedensity) result.append(myelinoverlay) root = settings2 filename = "Results.csv" fullpath = os.path.join(root, filename) f = open(fullpath, 'wb') writer = csv.writer(f) for d in range(len(result)): row = [result[d]] writer.writerows(row) f.close() # must be reset to 0 for each iteration. y = 0 r = 0 # if statistical analysis is being performed the results .csv file # is also saved to a subfolder within the statistical analysis folder # which denotes the experimental condition the results belong to. if stats is True: # nested for loop to identify correct experimental condition # for the current subfolder being analysed. for y in range(0, len(experiments)): for r in range(0, len(experiments[0])): if experiments[y][r] == subfoldernames[i]: if "Windows" in OS: root = imagefolder + "\\statistical analysis\\" + names[ y].getText() elif "Mac" in OS: root = imagefolder + "/statistical analysis/" + names[ y].getText() filename = subfoldernames[i] + ".csv" fullpath = os.path.join(root, filename) f = open(fullpath, 'wb') writer = csv.writer(f) for e in range(len(result)): row = [result[e]] writer.writerows(row) f.close() break cwd2 = os.getcwd() for files in os.listdir(cwd2): if files.endswith(".csv"): os.remove(os.path.join(cwd2, files)) imagenames = [] myelinoverlay = [] neuritedensity = [] # create .csv summary sheet with average % neurite density # and average % myelination for each subfolder (experiment). if multi is True: name = "Folder name" imagenames = [name] + subfoldernames neuritedensity = [red] + neuriteaverage2 myelinoverlay = [green] + myelinaverage2 result = [] result.append(imagenames) result.append(neuritedensity) result.append(myelinoverlay) if "Windows" in OS: root = imagefolder + "\\" elif "Mac" in OS: root = imagefolder + "/" filename = "Result-Summary.csv" fullpath = os.path.join(root, filename) f = open(fullpath, 'wb') writer = csv.writer(f) for p in range(len(result)): row = [result[p]] writer.writerows(row) f.close() imagenames = [] myelinoverlay = [] neuritedensity = [] # Run Rscript for statistical analysis via the command line if stats is True: cmd = Rloc2 + " " + cwdR + " " + statsfolderPath Runtime.getRuntime().exec(cmd) Finished()
def runOneTif(tifPath, dstTifPath): bPrintLog('=== runOneTif processing tif:' + tifPath, 3) bPrintLog('Loading file...', 3) imp = IJ.openImage(tifPath) if imp is None: bPrintLog('ERROR: could not open image from file:' + tifPath, 3) return 0 logStr = 'done loading file: ' + str(imp.width) + ' ' + str( imp.height) + ' ' + str(imp.getNSlices()) bPrintLog(logStr, 3) numSlices = imp.getNSlices() bPrintLog('numSlices: ' + str(numSlices), 3) infoStr = imp.getProperty("Info") #get all tags if infoStr is None: infoStr = '' infoStr += 'bMaxProject=v0.1\n' imp.setProperty("Info", infoStr) imp.show() impWin = imp.getTitle() # BODY # get the bit depth form opened imp impBitDepth = imp.getBitDepth() bPrintLog('image bit depth:' + str(impBitDepth), 3) # get the actual bit depth used (e.g. ScanImage is 11 bit, Prairie is 13 bit) header = bParseHeader(imp) actualBitDepth = impBitDepth if 'b_bitDepth' in header: actualBitDepth = int(header['b_bitDepth']) bPrintLog('actual bit depth:' + str(actualBitDepth), 3) made8bit = 0 if impBitDepth == 8: made8bit = 1 else: made8bit = 1 if 0: divideBy = math.pow(2, actualBitDepth) / math.pow( 2, 8) # divide the 13 bit or 11 bit image down to 8 bit bPrintLog('diving by:' + str(divideBy), 3) bPrintLog( 'converting to 8-bit by dividing image by ' + str(divideBy) + ' and then convert to 8-bit with ImageConverter.setDoScaling(False)', 3) #run("Divide...", "value=32 stack"); divideArgs = 'value=' + str(divideBy) + ' stack' IJ.run(imp, "Divide...", divideArgs) # convert to 8-bit will automatically scale, to turn this off use # eval("script", "ImageConverter.setDoScaling(false)"); # 20170810 was this #ImageConverter.setDoScaling(False) ImageConverter.setDoScaling(True) # run("8-bit"); bPrintLog('converting to 8-bit with setDoScaling False', 3) IJ.run(imp, "8-bit", '') #does this in place, no new window # save bPrintLog('Saving stack with ' + str(numSlices) + ' slices:' + dstTifPath, 3) fs = FileSaver(imp) if numSlices > 1: fs.saveAsTiffStack(dstTifPath) else: fs.saveAsTiff(dstTifPath) # END BODY # close original imp.changes = 0 imp.close()
from ij.plugin import RGBStackMerge from loci.plugins import BF from loci.plugins.in import ImporterOptions import os,sys path = '/Users/justin/UTS/Research/microscopy/' filetab = '%s/ijfiles' %path for l in open(filetab): f = l.strip().split() out = f[0] ch1 = '%s/%s' %(path,f[1]) ch2 = '%s/%s' %(path,f[2]) print('%s: opening %s and %s' %(out,ch1,ch2)) ch1 = ij.IJ.openImage(ch1) conv = ImageConverter(ch1) conv.convertToGray16() # ch1.show() ch2 = ij.IJ.openImage(ch2) conv = ImageConverter(ch2) conv.convertToGray16() # ch2.show() # ch1.close() # ch2.close() mrg = RGBStackMerge.mergeChannels([ch1, ch2], False) # mrg.show() mrgf = '%s/%s.merged.tiff' %(path,out) ij.IJ.saveAs(mrg,"Tiff",mrgf) mrg.close() opts = ImporterOptions() opts.setId(mrgf)