Search in sources :

Example 76 with ImagePlus

use of ij.ImagePlus in project TrakEM2 by trakem2.

the class Segmentation method fastMarching.

public static Bureaucrat fastMarching(final AreaWrapper aw, final Layer layer, final Rectangle srcRect, final int x_p_w, final int y_p_w, final List<Runnable> post_tasks) {
    // Capture pointers before they are set to null
    final AreaContainer ac = (AreaContainer) aw.getSource();
    final AffineTransform source_aff = aw.getSource().getAffineTransform();
    final Rectangle box = new Rectangle(x_p_w - Segmentation.fmp.width / 2, y_p_w - Segmentation.fmp.height / 2, Segmentation.fmp.width, Segmentation.fmp.height);
    Bureaucrat burro = Bureaucrat.create(new Worker.Task("Fast marching") {

        public void exec() {
            // Capture image as large as the fmp width,height centered on x_p_w,y_p_w
            Utils.log2("fmp box is " + box);
            ImagePlus imp = new ImagePlus("", Patch.makeFlatImage(ImagePlus.GRAY8, layer, box, 1.0, (Collection) layer.getDisplayables(Patch.class, new Area(box), true), Color.black));
            // Bandpass filter
            if (fmp.apply_bandpass_filter) {
                IJ.run(imp, "Bandpass Filter...", "filter_large=" + fmp.low_frequency_threshold + " filter_small=" + fmp.high_frequency_threshold + " suppress=None tolerance=5" + (fmp.autoscale_after_filtering ? " autoscale" : "") + (fmp.saturate_when_autoscaling ? " saturate" : ""));
            }
            // Setup seed point
            PointRoi roi = new PointRoi(box.width / 2, box.height / 2);
            imp.setRoi(roi);
            Utils.log2("imp: " + imp);
            Utils.log2("proi: " + imp.getRoi() + "    " + Utils.toString(new int[] { x_p_w - srcRect.x, y_p_w - srcRect.y }));
            // Setup state
            ImageContainer ic = new ImageContainer(imp);
            StateContainer state = new StateContainer();
            state.setROI(roi, ic.getWidth(), ic.getHeight(), ic.getImageCount(), imp.getCurrentSlice());
            state.setExpansionToInside(false);
            // Run FastMarching
            final FastMarching fm = new FastMarching(ic, null, state, true, fmp.fm_grey, fmp.fm_dist, fmp.apply_grey_value_erosion);
            final int max_iterations = fmp.max_iterations;
            final int iter_inc = fmp.iter_inc;
            for (int i = 0; i < max_iterations; i++) {
                if (Thread.currentThread().isInterrupted()) {
                    return;
                }
                if (!fm.step(iter_inc))
                    break;
            }
            // Extract ROI
            setTaskName("Adding area");
            final ArrayList<Coordinate> vc = fm.getStateContainer().getXYZ(false);
            if (0 == vc.size()) {
                Utils.log("No area growth.");
                return;
            }
            final Area area = new Area();
            Coordinate first = vc.remove(0);
            final Rectangle r = new Rectangle(first.x, first.y, 1, 1);
            int count = 0;
            // Scan and add line-wise
            for (final Coordinate c : vc) {
                count++;
                if (c.y == r.y && c.x == r.x + 1) {
                    // same line:
                    r.width += 1;
                    continue;
                } else {
                    // add previous one
                    area.add(new Area(r));
                }
                // start new line:
                r.x = c.x;
                r.y = c.y;
                r.width = 1;
                if (0 == count % 1024 && Thread.currentThread().isInterrupted()) {
                    return;
                }
            }
            // add last:
            area.add(new Area(r));
            /*
			// Trying from the image mask: JUST AS SLOW
			final byte[] b = (byte[]) fm.getStateContainer().getIPMask()[0].getPixels();
			final int w = imp.getWidth();
			for (int i=0; i<b.length; i++) {
				if (0 == b[i]) {
					r.x = i%w;
					r.y = i/w;
					area.add(new Area(r));
				}
			}
			*/
            /* // DOESN'T FILL?
			// Trying to just get the contour, and then filling holes
			for (final Coordinate c : fm.getStateContainer().getXYZ(true)) {
				r.x = c.x;
				r.y = c.y;
				area.add(new Area(r));
			}
			Polygon pol = new Polygon();
			final float[] coords = new float[6];
			for (PathIterator pit = area.getPathIterator(null); !pit.isDone(); ) {
				switch (pit.currentSegment(coords)) {
					case PathIterator.SEG_MOVETO:
					case PathIterator.SEG_LINETO:
						pol.addPoint((int)coords[0], (int)coords[1]);
						break;
					case PathIterator.SEG_CLOSE:
						area.add(new Area(pol));
						// prepare next:
						pol = new Polygon();
						break;
					default:
						Utils.log2("WARNING: unhandled seg type.");
						break;
				}
				pit.next();
				if (pit.isDone()) {
					break;
				}
			}
			*/
            // / FAILS because by now AreaWrapper's source is null
            // aw.add(area, new AffineTransform(1, 0, 0, 1, box.x, box.y));
            // Instead, compose an Area that is local to the AreaWrapper's area
            final AffineTransform aff = new AffineTransform(1, 0, 0, 1, box.x, box.y);
            try {
                aff.preConcatenate(source_aff.createInverse());
            } catch (NoninvertibleTransformException nite) {
                IJError.print(nite);
                return;
            }
            aw.getArea().add(area.createTransformedArea(aff));
            ac.calculateBoundingBox(layer);
            Display.repaint(layer);
        }
    }, layer.getProject());
    if (null != post_tasks)
        for (Runnable task : post_tasks) burro.addPostTask(task);
    burro.goHaveBreakfast();
    return burro;
}
Also used : FastMarching(levelsets.algorithm.FastMarching) Rectangle(java.awt.Rectangle) ArrayList(java.util.ArrayList) Bureaucrat(ini.trakem2.utils.Bureaucrat) ImagePlus(ij.ImagePlus) ImageContainer(levelsets.ij.ImageContainer) NoninvertibleTransformException(java.awt.geom.NoninvertibleTransformException) Area(java.awt.geom.Area) StateContainer(levelsets.ij.StateContainer) Coordinate(levelsets.algorithm.Coordinate) AreaContainer(ini.trakem2.display.AreaContainer) AffineTransform(java.awt.geom.AffineTransform) Worker(ini.trakem2.utils.Worker) PointRoi(ij.gui.PointRoi)

Example 77 with ImagePlus

use of ij.ImagePlus in project TrakEM2 by trakem2.

the class StitchingTEM method correlate.

/**
 * @param scale For optimizing the speed of phase- and cross-correlation.
 * @param percent_overlap The minimum chunk of adjacent images to compare with, will automatically and gradually increase to 100% if no good matches are found.
 * @return a double[4] array containing:<ul>
 * <li>x2: relative X position of the second Patch</li>
 * <li>y2: relative Y position of the second Patch</li>
 * <li>flag: ERROR or SUCCESS</li>
 * <li>R: cross-correlation coefficient</li>
 * </ul>
 */
public static double[] correlate(final Patch base, final Patch moving, final float percent_overlap, final double scale, final int direction, final double default_dx, final double default_dy, final double min_R) {
    // PhaseCorrelation2D pc = null;
    final double R = -2;
    // final int limit = 5; // number of peaks to check in the PhaseCorrelation results
    // final float min_R = 0.40f; // minimum R for phase-correlation to be considered good
    // half this min_R will be considered good for cross-correlation
    // Iterate until PhaseCorrelation correlation coefficient R is over 0.5, or there's no more
    // image overlap to feed
    // Utils.log2("min_R: " + min_R);
    ImageProcessor ip1, ip2;
    final Rectangle b1 = base.getBoundingBox(null);
    final Rectangle b2 = moving.getBoundingBox(null);
    final int w1 = b1.width, h1 = b1.height, w2 = b2.width, h2 = b2.height;
    Roi roi1 = null, roi2 = null;
    float overlap = percent_overlap;
    double dx = default_dx, dy = default_dy;
    do {
        // create rois for the stripes
        switch(direction) {
            case TOP_BOTTOM:
                // bottom
                roi1 = new Roi(0, h1 - (int) (h1 * overlap), w1, (int) (h1 * overlap));
                // top
                roi2 = new Roi(0, 0, w2, (int) (h2 * overlap));
                break;
            case LEFT_RIGHT:
                // right
                roi1 = new Roi(w1 - (int) (w1 * overlap), 0, (int) (w1 * overlap), h1);
                // left
                roi2 = new Roi(0, 0, (int) (w2 * overlap), h2);
                break;
        }
        // Utils.log2("roi1: " + roi1);
        // Utils.log2("roi2: " + roi2);
        // will apply the transform if necessary
        ip1 = makeStripe(base, roi1, scale);
        ip2 = makeStripe(moving, roi2, scale);
        // new ImagePlus("roi1", ip1).show();
        // new ImagePlus("roi2", ip2).show();
        ip1.setPixels(ImageFilter.computeGaussianFastMirror(new FloatArray2D((float[]) ip1.getPixels(), ip1.getWidth(), ip1.getHeight()), 1.0).data);
        ip2.setPixels(ImageFilter.computeGaussianFastMirror(new FloatArray2D((float[]) ip2.getPixels(), ip2.getWidth(), ip2.getHeight()), 1.0).data);
        // 
        final ImagePlus imp1 = new ImagePlus("", ip1);
        final ImagePlus imp2 = new ImagePlus("", ip2);
        final PhaseCorrelationCalculator t = new PhaseCorrelationCalculator(imp1, imp2);
        final PhaseCorrelationPeak peak = t.getPeak();
        final double resultR = peak.getCrossCorrelationPeak();
        final int[] peackPostion = peak.getPosition();
        final java.awt.Point shift = new java.awt.Point(peackPostion[0], peackPostion[1]);
        // Utils.log2("overlap: " + overlap + " R: " + resultR + " shift: " + shift + " dx,dy: " + dx + ", " + dy);
        if (resultR >= min_R) {
            // success
            final int success = SUCCESS;
            switch(direction) {
                case TOP_BOTTOM:
                    // boundary checks:
                    // if (shift.y/scale > default_dy) success = ERROR;
                    dx = shift.x / scale;
                    dy = roi1.getBounds().y + shift.y / scale;
                    break;
                case LEFT_RIGHT:
                    // boundary checks:
                    // if (shift.x/scale > default_dx) success = ERROR;
                    dx = roi1.getBounds().x + shift.x / scale;
                    dy = shift.y / scale;
                    break;
            }
            // Utils.log2("R: " + resultR + " shift: " + shift + " dx,dy: " + dx + ", " + dy);
            return new double[] { dx, dy, success, resultR };
        }
        // new ImagePlus("roi1", ip1.duplicate()).show();
        // new ImagePlus("roi2", ip2.duplicate()).show();
        // try { Thread.sleep(1000000000); } catch (Exception e) {}
        // increase for next iteration
        // increments of 10%
        overlap += 0.10;
    } while (R < min_R && Math.abs(overlap - 1.0f) < 0.001f);
    // Phase-correlation failed, fall back to cross-correlation with a safe overlap
    overlap = percent_overlap * 2;
    if (overlap > 1.0f)
        overlap = 1.0f;
    switch(direction) {
        case TOP_BOTTOM:
            // bottom
            roi1 = new Roi(0, h1 - (int) (h1 * overlap), w1, (int) (h1 * overlap));
            // top
            roi2 = new Roi(0, 0, w2, (int) (h2 * overlap));
            break;
        case LEFT_RIGHT:
            // right
            roi1 = new Roi(w1 - (int) (w1 * overlap), 0, (int) (w1 * overlap), h1);
            // left
            roi2 = new Roi(0, 0, (int) (w2 * overlap), h2);
            break;
    }
    // use one third of the size used for phase-correlation though! Otherwise, it may take FOREVER
    final double scale_cc = scale / 3.0f;
    ip1 = makeStripe(base, roi1, scale_cc);
    ip2 = makeStripe(moving, roi2, scale_cc);
    // gaussian blur them before cross-correlation
    ip1.setPixels(ImageFilter.computeGaussianFastMirror(new FloatArray2D((float[]) ip1.getPixels(), ip1.getWidth(), ip1.getHeight()), 1f).data);
    ip2.setPixels(ImageFilter.computeGaussianFastMirror(new FloatArray2D((float[]) ip2.getPixels(), ip2.getWidth(), ip2.getHeight()), 1f).data);
    // new ImagePlus("CC roi1", ip1).show();
    // new ImagePlus("CC roi2", ip2).show();
    final CrossCorrelation2D cc = new CrossCorrelation2D(ip1, ip2, false);
    double[] cc_result = null;
    switch(direction) {
        case TOP_BOTTOM:
            cc_result = cc.computeCrossCorrelationMT(0.9, 0.3, false);
            break;
        case LEFT_RIGHT:
            cc_result = cc.computeCrossCorrelationMT(0.3, 0.9, false);
            break;
    }
    if (cc_result[2] > min_R / 2) {
        // accepting if R is above half the R accepted for Phase Correlation
        // success
        final int success = SUCCESS;
        switch(direction) {
            case TOP_BOTTOM:
                // boundary checks:
                // if (cc_result[1]/scale_cc > default_dy) success = ERROR;
                dx = cc_result[0] / scale_cc;
                dy = roi1.getBounds().y + cc_result[1] / scale_cc;
                break;
            case LEFT_RIGHT:
                // boundary checks:
                // if (cc_result[0]/scale_cc > default_dx) success = ERROR;
                dx = roi1.getBounds().x + cc_result[0] / scale_cc;
                dy = cc_result[1] / scale_cc;
                break;
        }
        // Utils.log2("\trois: \t" + roi1 + "\n\t\t" + roi2);
        return new double[] { dx, dy, success, cc_result[2] };
    }
    // Utils.log2("Using default");
    return new double[] { default_dx, default_dy, ERROR, 0 };
// / ABOVE: boundary checks don't work if default_dx,dy are zero! And may actually be harmful in anycase
}
Also used : FloatArray2D(mpi.fruitfly.math.datastructures.FloatArray2D) Rectangle(java.awt.Rectangle) Point(mpicbg.models.Point) Roi(ij.gui.Roi) ImagePlus(ij.ImagePlus) Point(mpicbg.models.Point) ImageProcessor(ij.process.ImageProcessor) PhaseCorrelationPeak(mpicbg.imglib.algorithm.fft.PhaseCorrelationPeak) CrossCorrelation2D(mpi.fruitfly.registration.CrossCorrelation2D)

Example 78 with ImagePlus

use of ij.ImagePlus in project TrakEM2 by trakem2.

the class ContrastEnhancerWrapper method apply.

public boolean apply(final Collection<Displayable> patches_) {
    if (null == patches_)
        return false;
    // Create appropriate patch list
    ArrayList<Patch> patches = new ArrayList<Patch>();
    for (final Displayable d : patches_) {
        if (d.getClass() == Patch.class)
            patches.add((Patch) d);
    }
    if (0 == patches.size())
        return false;
    // Check that all images are of the same size and type
    Patch firstp = (Patch) patches.get(0);
    final int ptype = firstp.getType();
    final double pw = firstp.getOWidth();
    final double ph = firstp.getOHeight();
    for (final Patch p : patches) {
        if (p.getType() != ptype) {
            // can't continue
            Utils.log("Can't homogenize histograms: images are not all of the same type.\nFirst offending image is: " + p);
            return false;
        }
        if (!equalize && 0 == stats_mode && p.getOWidth() != pw || p.getOHeight() != ph) {
            Utils.log("Can't homogenize histograms: images are not all of the same size.\nFirst offending image is: " + p);
            return false;
        }
    }
    try {
        if (equalize) {
            for (final Patch p : patches) {
                if (Thread.currentThread().isInterrupted())
                    return false;
                p.appendFilters(new IFilter[] { new EqualizeHistogram() });
                /*
					p.getProject().getLoader().releaseToFit(p.getOWidth(), p.getOHeight(), p.getType(), 3);
					ImageProcessor ip = p.getImageProcessor().duplicate(); // a throw-away copy
					if (this.from_existing_min_and_max) {
						ip.setMinAndMax(p.getMin(), p.getMax());
					}
					ce.equalize(ip);
					p.setMinAndMax(ip.getMin(), ip.getMax());
					*/
                // submit for regeneration
                p.getProject().getLoader().decacheImagePlus(p.getId());
                regenerateMipMaps(p);
            }
            return true;
        }
        // Else, call stretchHistogram with an appropriate stats object
        final ImageStatistics stats;
        if (1 == stats_mode) {
            // use each image independent stats
            stats = null;
        } else if (0 == stats_mode) {
            // use stack statistics
            final ArrayList<Patch> sub = new ArrayList<Patch>();
            if (use_full_stack) {
                sub.addAll(patches);
            } else {
                // build stack statistics, ordered by stdDev
                final SortedMap<Stats, Patch> sp = Collections.synchronizedSortedMap(new TreeMap<Stats, Patch>());
                Process.progressive(patches, new TaskFactory<Patch, Stats>() {

                    public Stats process(final Patch p) {
                        if (Thread.currentThread().isInterrupted())
                            return null;
                        ImagePlus imp = p.getImagePlus();
                        p.getProject().getLoader().releaseToFit(p.getOWidth(), p.getOHeight(), p.getType(), 2);
                        Stats s = new Stats(imp.getStatistics());
                        sp.put(s, p);
                        return s;
                    }
                });
                if (Thread.currentThread().isInterrupted())
                    return false;
                final ArrayList<Patch> a = new ArrayList<Patch>(sp.values());
                final int count = a.size();
                if (count < 3) {
                    sub.addAll(a);
                } else if (3 == count) {
                    // the middle one
                    sub.add(a.get(1));
                } else if (4 == count) {
                    sub.addAll(a.subList(1, 3));
                } else if (count > 4) {
                    int first = (int) (count / 4.0 + 0.5);
                    int last = (int) (count / 4.0 * 3 + 0.5);
                    sub.addAll(a.subList(first, last));
                }
            }
            stats = new StackStatistics(new PatchStack(sub.toArray(new Patch[sub.size()]), 1));
        } else {
            stats = reference_stats;
        }
        final Calibration cal = patches.get(0).getLayer().getParent().getCalibrationCopy();
        Process.progressive(patches, new TaskFactory<Patch, Object>() {

            public Object process(final Patch p) {
                if (Thread.currentThread().isInterrupted())
                    return null;
                p.getProject().getLoader().releaseToFit(p.getOWidth(), p.getOHeight(), p.getType(), 3);
                // a throw-away copy
                ImageProcessor ip = p.getImageProcessor().duplicate();
                if (ContrastEnhancerWrapper.this.from_existing_min_and_max) {
                    ip.setMinAndMax(p.getMin(), p.getMax());
                }
                ImageStatistics st = stats;
                if (null == stats) {
                    Utils.log2("Null stats, using image's self");
                    st = ImageStatistics.getStatistics(ip, Measurements.MIN_MAX, cal);
                }
                ce.stretchHistogram(ip, saturated, st);
                // This is all we care about from stretching the histogram:
                p.setMinAndMax(ip.getMin(), ip.getMax());
                regenerateMipMaps(p);
                return null;
            }
        });
    } catch (Exception e) {
        IJError.print(e);
        return false;
    }
    return true;
}
Also used : Displayable(ini.trakem2.display.Displayable) ArrayList(java.util.ArrayList) StackStatistics(ij.process.StackStatistics) Calibration(ij.measure.Calibration) TreeMap(java.util.TreeMap) ImagePlus(ij.ImagePlus) ImageProcessor(ij.process.ImageProcessor) ImageStatistics(ij.process.ImageStatistics) SortedMap(java.util.SortedMap) TaskFactory(ini.trakem2.parallel.TaskFactory) EqualizeHistogram(ini.trakem2.imaging.filters.EqualizeHistogram) Patch(ini.trakem2.display.Patch)

Example 79 with ImagePlus

use of ij.ImagePlus in project TrakEM2 by trakem2.

the class IntegralHistogram2d method view.

@SuppressWarnings("unused")
private static final void view(final long[] hist, final int w1, final int h1, final int nBins) {
    final float[] pixels = new float[w1 * h1 * nBins];
    for (int i = 0; i < hist.length; ++i) {
        pixels[i] = hist[i];
    }
    new ImagePlus("Integral Histogram", new FloatProcessor(w1 * nBins, h1, pixels)).show();
}
Also used : FloatProcessor(ij.process.FloatProcessor) ImagePlus(ij.ImagePlus)

Example 80 with ImagePlus

use of ij.ImagePlus in project TrakEM2 by trakem2.

the class LayerStack method getProcessor.

/**
 * Returns an ImageProcessor for the specified slice,
 *		where {@code 1<=n<=nslices}. Returns null if the stack is empty.
 */
@Override
public ImageProcessor getProcessor(int n) {
    if (n < 1 || n > layers.size())
        return null;
    // Create a flat image on the fly with everything on it, and return its processor.
    final Layer layer = layers.get(n - 1);
    final Loader loader = layer.getProject().getLoader();
    Long cid;
    synchronized (id_cache) {
        cid = id_cache.get(layer.getId());
        if (null == cid) {
            cid = loader.getNextTempId();
            id_cache.put(layer.getId(), cid);
        }
    }
    ImageProcessor ip;
    synchronized (cid) {
        ImagePlus imp = loader.getCachedImagePlus(cid);
        if (null == imp || null == imp.getProcessor() || null == imp.getProcessor().getPixels()) {
            ip = loader.getFlatImage(layer, this.roi, this.scale, this.c_alphas, this.type, this.clazz, null).getProcessor();
            if (invert)
                ip.invert();
            loader.cacheImagePlus(cid, new ImagePlus("", ip));
        } else
            ip = imp.getProcessor();
    }
    return ip;
}
Also used : ImageProcessor(ij.process.ImageProcessor) Loader(ini.trakem2.persistence.Loader) Layer(ini.trakem2.display.Layer) ImagePlus(ij.ImagePlus)

Aggregations

ImagePlus (ij.ImagePlus)363 ImageStack (ij.ImageStack)85 ImageProcessor (ij.process.ImageProcessor)74 Rectangle (java.awt.Rectangle)60 ArrayList (java.util.ArrayList)46 IOException (java.io.IOException)40 File (java.io.File)36 Roi (ij.gui.Roi)32 Point (java.awt.Point)32 ByteProcessor (ij.process.ByteProcessor)29 FormatException (loci.formats.FormatException)29 GenericDialog (ij.gui.GenericDialog)27 Calibration (ij.measure.Calibration)26 FloatProcessor (ij.process.FloatProcessor)22 Future (java.util.concurrent.Future)22 ExtendedGenericDialog (uk.ac.sussex.gdsc.core.ij.gui.ExtendedGenericDialog)22 LinkedList (java.util.LinkedList)21 ExecutorService (java.util.concurrent.ExecutorService)19 MemoryPeakResults (uk.ac.sussex.gdsc.smlm.results.MemoryPeakResults)19 PointRoi (ij.gui.PointRoi)17