def translate_single_stack_using_imglib2(imp, dx, dy, dz): # wrap into a float imglib2 and translate # conversion into float is necessary due to "overflow of n-linear interpolation due to accuracy limits of unsigned bytes" # see: https://github.com/fiji/fiji/issues/136#issuecomment-173831951 img = ImagePlusImgs.from(imp.duplicate()) extended = Views.extendZero(img) converted = Converters.convert(extended, RealFloatSamplerConverter()) interpolant = Views.interpolate(converted, NLinearInterpolatorFactory()) # translate if imp.getNDimensions()==3: transformed = RealViews.affine(interpolant, Translation3D(dx, dy, dz)) elif imp.getNDimensions()==2: transformed = RealViews.affine(interpolant, Translation2D(dx, dy)) else: IJ.log("Can only work on 2D or 3D stacks") return None cropped = Views.interval(transformed, img) # wrap back into bit depth of input image and return bd = imp.getBitDepth() if bd==8: return(ImageJFunctions.wrapUnsignedByte(cropped,"imglib2")) elif bd == 16: return(ImageJFunctions.wrapUnsignedShort(cropped,"imglib2")) elif bd == 32: return(ImageJFunctions.wrapFloat(cropped,"imglib2")) else: return None
def asBackwardConcatTransforms(matrices, transformclass=AffineTransform3D): """ Transforms are img1 -> img2, and we want the opposite: so invert each. Also, each image was registered to the previous, so must concatenate all previous transforms. """ # Special-case for speed if transformclass == Translation3D: tx, ty, tz = 0.0, 0.0, 0.0 translations = [] for matrix in matrices: # Subtract: same as inverse tx -= matrix[3] ty -= matrix[7] tz -= matrix[11] translations.append(Translation3D(tx, ty, tz)) return translations # Else, use AffineTransform3D aff_previous = transformclass() # It's puzzling that AffineTransform3D is not initialized to identity aff_previous.identity() # set to identity affines = [aff_previous] # first image at index 0 gets identity for matrix in matrices[1:]: # skip zero aff = AffineTransform3D() aff.set(*matrix) aff = aff.inverse( ) # transform defines img1 -> img2, we want the opposite aff.preConcatenate(aff_previous) # Make relative to prior image affines.append(aff) # Store aff_previous = aff # next iteration return affines
def translatedView(img, matrix): imgE = Views.extendZero(img) imgI = Views.interpolate(imgE, NLinearInterpolatorFactory()) # In negative: the inverse t = Translation3D(-matrix[3], -matrix[7], -matrix[11]) imgT = RealViews.transform(imgI, t) return Views.interval(imgT, [0, 0, 0], [img.dimension(d) for d in xrange(3)])
def translate_using_imglib2(imp, dx, dy, dz): print "imp channels",imp.getNChannels() # todo: # if multiple channels use Duplicator to translate each channel individually ## wrap # http://javadoc.imagej.net/ImgLib2/net/imglib2/img/imageplus/ImagePlusImg.html img = ImagePlusImgs.from(imp.duplicate()) print "dimensions:",img.numDimensions() print img.getChannels() ## prepare image print "img",img ddd extended = Views.extendBorder(img) #print "extended",extended #print "extended",extended.dimension(1) dims = zeros(4, 'l') img.dimensions(dims) print "dims",dims converted = Converters.convert(extended, RealFloatSamplerConverter()) composite = Views.collapseReal(converted, imp.getNChannels()) print "composite",composite interpolant = Views.interpolate(composite, NLinearInterpolatorFactory()) #print "interpolant",interpolant transformed = RealViews.affine(interpolant, Translation3D(dx, dy, dz)) print "transformed", transformed cropped = Views.interval(transformed, img) print "cropped.numDimensions()", cropped.numDimensions() print "cropped",cropped ## wrap back and return bd = imp.getBitDepth() # maybe simply wrap works? if bd==8: return(ImageJFunctions.wrapUnsignedByte(cropped,"imglib2")) elif bd == 16: return(ImageJFunctions.wrapUnsignedShort(cropped,"imglib2")) elif bd == 32: return(ImageJFunctions.wrapFloat(cropped,"imglib2")) else: return None
try: # Compare all to all for view1, view2 in combinations(img_names, 2): _, matrix = computeForwardTransforms([view1, view2], ImgLoader(), getCalibration, csv_dir, exe, modelclass, params, exe_shutdown=False) print "%s, %s:\n[%s,\n %s,\n %s]" % (view1, view2, str(matrix[0:4].tolist()), str(matrix[4:8].tolist()), str(matrix[8:].tolist())) matrices[view1 + "-" + view2] = matrix finally: exe.shutdown() # Assume translation is small: same enclosing interval def translatedView(img, matrix): imgE = Views.extendZero(img) imgI = Views.interpolate(imgE, NLinearInterpolatorFactory()) # In negative: the inverse t = Translation3D(-matrix[3], -matrix[7], -matrix[11]) imgT = RealViews.transform(imgI, t) return Views.interval(imgT, [0, 0, 0], [img.dimension(d) for d in xrange(3)]) def transformedView(img, matrix): imgE = Views.extendZero(img) imgI = Views.interpolate(imgE, NLinearInterpolatorFactory()) aff = AffineTransform3D() aff.set(*matrix) # Because matrix defines a forward transform and for rendering relative to CM00 a backward one is needed aff = aff.inverse() imgT = RealViews.transform(imgI, aff) return Views.interval(imgT, [0, 0, 0], [img.dimension(d) for d in xrange(3)]) if TranslationModel3D == modelclass: transformed = [ imgB0,