use of ini.trakem2.display.Layer in project TrakEM2 by trakem2.
the class Patch method mousePressed.
@Override
public void mousePressed(final MouseEvent me, final Layer la, final int x_p, final int y_p, final double mag) {
final int tool = ProjectToolbar.getToolId();
final DisplayCanvas canvas = (DisplayCanvas) me.getSource();
if (ProjectToolbar.WAND == tool) {
if (null == canvas)
return;
Bureaucrat.createAndStart(new Worker.Task("Magic Wand ROI") {
@Override
public void exec() {
final PatchImage pai = createTransformedImage();
pai.target.setMinAndMax(min, max);
final ImagePlus patchImp = new ImagePlus("", pai.target.convertToByte(true));
final double[] fp = new double[2];
fp[0] = x_p;
fp[1] = y_p;
try {
at.createInverse().transform(fp, 0, fp, 0, 1);
} catch (final NoninvertibleTransformException e) {
IJError.print(e);
return;
}
final int npoints = IJ.doWand(patchImp, (int) fp[0], (int) fp[1], WandToolOptions.getTolerance(), WandToolOptions.getMode());
if (npoints > 0) {
System.out.println("npoints " + npoints);
final Roi roi = patchImp.getRoi();
if (null != roi) {
final Area aroi = M.getArea(roi);
aroi.transform(at);
canvas.getFakeImagePlus().setRoi(new ShapeRoi(aroi));
}
}
}
}, project);
}
}
use of ini.trakem2.display.Layer in project TrakEM2 by trakem2.
the class Polyline method mousePressed.
@Override
public void mousePressed(final MouseEvent me, final Layer layer, int x_p, int y_p, final double mag) {
// transform the x_p, y_p to the local coordinates
final int x_pd = x_p;
final int y_pd = y_p;
if (!this.at.isIdentity()) {
final Point2D.Double po = inverseTransformPoint(x_p, y_p);
x_p = (int) po.x;
y_p = (int) po.y;
}
final int tool = ProjectToolbar.getToolId();
final Display display = ((DisplayCanvas) me.getSource()).getDisplay();
final long layer_id = layer.getId();
index = findPoint(x_p, y_p, layer_id, mag);
if (ProjectToolbar.PENCIL == tool && n_points > 0 && -1 == index && !me.isShiftDown() && !Utils.isControlDown(me)) {
// Check that there are any images -- otherwise may hang. TODO
if (layer_set.getDisplayables(Patch.class).isEmpty()) {
Utils.log("No images are present!");
return;
}
final double scale = layer_set.getVirtualizationScale();
// Ok now with all found images, create a virtual stack that provides access to them all, with caching.
final Worker[] worker = new Worker[2];
final TraceParameters tr_ = tr_map.get(layer_set);
final TraceParameters tr = null == tr_ ? new TraceParameters() : tr_;
if (null == tr_) {
synchronized (tr_map) {
tr_map.put(layer_set, tr);
}
}
if (tr.update) {
worker[0] = new Worker("Preparing Hessian...") {
@Override
public void run() {
startedWorking();
try {
Utils.log("Push ESCAPE key to cancel autotrace anytime.");
final ImagePlus virtual = new LayerStack(layer_set, scale, ImagePlus.GRAY8, Patch.class, display.getDisplayChannelAlphas(), Segmentation.fmp.SNT_invert_image).getImagePlus();
// virtual.show();
final Calibration cal = virtual.getCalibration();
double minimumSeparation = 1;
if (cal != null)
minimumSeparation = Math.min(cal.pixelWidth, Math.min(cal.pixelHeight, cal.pixelDepth));
final ComputeCurvatures hessian = new ComputeCurvatures(virtual, minimumSeparation, null, cal != null);
hessian.run();
tr.virtual = virtual;
// tr.scale = scale;
tr.hessian = hessian;
tr.update = false;
} catch (final Exception e) {
IJError.print(e);
}
finishedWorking();
}
};
Bureaucrat.createAndStart(worker[0], project);
}
final Point2D.Double po = transformPoint(p[0][n_points - 1], p[1][n_points - 1]);
final int start_x = (int) po.x;
final int start_y = (int) po.y;
// 0-based
final int start_z = layer_set.indexOf(layer_set.getLayer(p_layer[n_points - 1]));
// must transform into virtual space
final int goal_x = (int) (x_pd * scale);
final int goal_y = (int) (y_pd * scale);
final int goal_z = layer_set.indexOf(layer);
/*
Utils.log2("x_pd, y_pd : " + x_pd + ", " + y_pd);
Utils.log2("scale: " + scale);
Utils.log2("start: " + start_x + "," + start_y + ", " + start_z);
Utils.log2("goal: " + goal_x + "," + goal_y + ", " + goal_z);
Utils.log2("virtual: " + tr.virtual);
*/
final boolean simplify = me.isAltDown();
worker[1] = new Worker("Tracer - waiting on hessian") {
@Override
public void run() {
startedWorking();
try {
if (null != worker[0]) {
// Wait until hessian is ready
worker[0].join();
}
setTaskName("Tracing path");
final int reportEveryMilliseconds = 2000;
tr.tracer = new TracerThread(tr.virtual, 0, 255, // timeout seconds
120, reportEveryMilliseconds, start_x, start_y, start_z, goal_x, goal_y, goal_z, // reciproal pix values at start and goal
true, tr.virtual.getStackSize() == 1, tr.hessian, null == tr.hessian ? 1 : 4, null, null != tr.hessian);
tr.tracer.addProgressListener(new SearchProgressCallback() {
@Override
public void pointsInSearch(final SearchInterface source, final int inOpen, final int inClosed) {
worker[1].setTaskName("Tracing path: open=" + inOpen + " closed=" + inClosed);
}
@Override
public void finished(final SearchInterface source, final boolean success) {
if (!success) {
Utils.logAll("Could NOT trace a path");
}
}
@Override
public void threadStatus(final SearchInterface source, final int currentStatus) {
// This method gets called every reportEveryMilliseconds
if (worker[1].hasQuitted()) {
source.requestStop();
}
}
});
tr.tracer.run();
final Path result = tr.tracer.getResult();
tr.tracer = null;
if (null == result) {
// : "+
Utils.log("Finding a path failed");
// not public //SearchThread.exitReasonStrings[tracer.getExitReason()]);
return;
}
// TODO: precise_x_positions etc are likely to be broken (calibrated or something)
// Remove bogus points: those at the end with 0,0 coords
int len = result.points;
final double[][] pos = result.getXYZUnscaled();
for (int i = len - 1; i > -1; i--) {
if (0 == pos[0][i] && 0 == pos[1][i]) {
len--;
} else
break;
}
// Transform points: undo scale, and bring to this Polyline AffineTransform:
final AffineTransform aff = new AffineTransform();
/* Inverse order: */
/* 2 */
aff.concatenate(Polyline.this.at.createInverse());
/* 1 */
aff.scale(1 / scale, 1 / scale);
final double[] po = new double[len * 2];
for (int i = 0, j = 0; i < len; i++, j += 2) {
po[j] = pos[0][i];
po[j + 1] = pos[1][i];
}
final double[] po2 = new double[len * 2];
// what a stupid format: consecutive x,y pairs
aff.transform(po, 0, po2, 0, len);
long[] p_layer_ids = new long[len];
double[] pox = new double[len];
double[] poy = new double[len];
for (int i = 0, j = 0; i < len; i++, j += 2) {
// z_positions in 0-(N-1), not in 1-N like slices!
p_layer_ids[i] = layer_set.getLayer((int) pos[2][i]).getId();
pox[i] = po2[j];
poy[i] = po2[j + 1];
}
// Simplify path: to steps of 5 calibration units, or 5 pixels when not calibrated.
if (simplify) {
setTaskName("Simplifying path");
final Object[] ob = Polyline.simplify(pox, poy, p_layer_ids, 10000, layer_set);
pox = (double[]) ob[0];
poy = (double[]) ob[1];
p_layer_ids = (long[]) ob[2];
len = pox.length;
}
// Record the first newly-added autotraced point index:
last_autotrace_start = Polyline.this.n_points;
Polyline.this.appendPoints(pox, poy, p_layer_ids, len);
Polyline.this.repaint(true, null);
Utils.logAll("Added " + len + " new points.");
} catch (final Exception e) {
IJError.print(e);
}
finishedWorking();
}
};
Bureaucrat.createAndStart(worker[1], project);
index = -1;
return;
}
if (ProjectToolbar.PEN == tool || ProjectToolbar.PENCIL == tool) {
if (Utils.isControlDown(me) && me.isShiftDown()) {
final long lid = Display.getFrontLayer(this.project).getId();
if (-1 == index || lid != p_layer[index]) {
index = findNearestPoint(x_p, y_p, layer_id);
}
if (-1 != index) {
// delete point
removePoint(index);
index = -1;
repaint(false, null);
}
// In any case, terminate
return;
}
if (// disable!
-1 != index && layer_id != p_layer[index])
// disable!
index = -1;
else // if no conditions are met, attempt to add point
if (-1 == index && !me.isShiftDown() && !me.isAltDown()) {
// add a new point
index = addPoint(x_p, y_p, layer_id, mag);
is_new_point = true;
repaint(false, null);
return;
}
}
}
use of ini.trakem2.display.Layer in project TrakEM2 by trakem2.
the class StitchingTEM method montageWithPhaseCorrelation.
/**
* @param layers
* @param worker Optional, the {@link Worker} running this task.
*/
public static void montageWithPhaseCorrelation(final List<Layer> layers, final Worker worker) {
final PhaseCorrelationParam param = new PhaseCorrelationParam();
final Collection<Displayable> col = layers.get(0).getDisplayables(Patch.class);
if (!param.setup(col.size() > 0 ? (Patch) col.iterator().next() : null)) {
return;
}
final int i = 1;
for (final Layer la : layers) {
if (Thread.currentThread().isInterrupted() || (null != worker && worker.hasQuitted()))
return;
if (null != worker)
worker.setTaskName("Montage layer " + i + "/" + layers.size());
final Collection<Patch> patches = (Collection<Patch>) (Collection) la.getDisplayables(Patch.class);
AlignTask.transformPatchesAndVectorData(patches, new Runnable() {
@Override
public void run() {
montageWithPhaseCorrelation(patches, param);
}
});
}
}
use of ini.trakem2.display.Layer in project TrakEM2 by trakem2.
the class ControlClickBehavior method doProcess.
@Override
public void doProcess(final MouseEvent e) {
if (!e.isControlDown() || e.getID() != MouseEvent.MOUSE_PRESSED) {
super.doProcess(e);
return;
}
final Picker picker = universe.getPicker();
final Content content = picker.getPickedContent(e.getX(), e.getY());
if (content == null)
return;
final Point3d p = picker.getPickPointGeometry(content, e);
if (p == null) {
Utils.log("No point was found on content " + content);
return;
}
final Display display = Display.getFront(ls.getProject());
if (display == null) {
// If there's no Display, just return...
return;
}
if (display.getLayerSet() != ls) {
Utils.log("The LayerSet instances do not match");
return;
}
if (ls == null) {
Utils.log("No LayerSet was found for the Display");
return;
}
final Calibration cal = ls.getCalibration();
if (cal == null) {
Utils.log("No calibration information was found for the LayerSet");
return;
}
final double scaledZ = p.z / cal.pixelWidth;
final Layer l = ls.getNearestLayer(scaledZ);
if (l == null) {
Utils.log("No layer was found nearest to " + scaledZ);
return;
}
final Coordinate<?> coordinate = new Coordinate<Object>(p.x / cal.pixelWidth, p.y / cal.pixelHeight, l, null);
display.center(coordinate);
}
use of ini.trakem2.display.Layer in project TrakEM2 by trakem2.
the class AmiraImporter method extractAreaLists.
/**
* Returns a map of label vs AreaList.
*/
public static Map<Float, AreaList> extractAreaLists(final ImagePlus imp, final Layer first_layer, final double base_x, final double base_y, final float alpha, final boolean add_background) {
try {
final HashMap<Integer, HashMap<Float, Area>> map = new HashMap<Integer, HashMap<Float, Area>>();
// works even for images that are not stacks: it creates one
final ImageStack stack = imp.getStack();
final AtomicInteger ai = new AtomicInteger(1);
final AtomicInteger completed_slices = new AtomicInteger(0);
final int n_slices = imp.getNSlices();
final Thread parent = Thread.currentThread();
final Thread[] threads = MultiThreading.newThreads();
for (int ithread = 0; ithread < threads.length; ithread++) {
threads[ithread] = new Thread() {
public void run() {
final Rectangle box = new Rectangle(0, 0, 1, 1);
for (int i = ai.getAndIncrement(); i <= n_slices; i = ai.getAndIncrement()) {
final ImageProcessor ip;
synchronized (map) {
ip = stack.getProcessor(i);
}
if (parent.isInterrupted())
return;
final HashMap<Float, Area> layer_map = new HashMap<Float, Area>();
synchronized (map) {
map.put(i, layer_map);
}
AreaUtils.extractAreas(ip, layer_map, add_background, box, parent, true);
Utils.showProgress(completed_slices.incrementAndGet() / (float) n_slices);
}
}
};
}
MultiThreading.startAndJoin(threads);
Utils.showProgress(1);
if (parent.isInterrupted())
return null;
final HashMap<Float, AreaList> alis = new HashMap<Float, AreaList>();
Utils.log2("Recreating arealists...");
Utils.log2("map.size() = " + map.size());
final double thickness = first_layer.getThickness();
final double first_z = first_layer.getZ();
// Recreate AreaLists
for (final Map.Entry<Integer, HashMap<Float, Area>> e : map.entrySet()) {
final int slice_index = e.getKey();
final HashMap<Float, Area> layer_map = e.getValue();
for (final Map.Entry<Float, Area> fa : layer_map.entrySet()) {
Float label = fa.getKey();
AreaList ali = alis.get(label);
if (null == ali) {
ali = new AreaList(first_layer.getProject(), "Label " + label.intValue(), base_x, base_y);
alis.put(label, ali);
}
double z = first_z + (slice_index - 1) * thickness;
Layer layer = first_layer.getParent().getLayer(z, thickness, true);
ali.setArea(layer.getId(), fa.getValue());
}
}
Utils.log2("Done recreating.");
first_layer.getParent().addAll(alis.values());
Utils.log2("Done adding all to LayerSet");
float hue = 0;
for (final Map.Entry<Float, AreaList> e : alis.entrySet()) {
final AreaList ali = e.getValue();
ali.setProperty("label", Integer.toString(e.getKey().intValue()));
ali.calculateBoundingBox(null);
ali.setColor(Color.getHSBColor(hue, 1, 1));
ali.setAlpha(alpha);
// golden angle
hue += 0.38197f;
if (hue > 1)
hue = hue - 1;
}
Utils.log2("Done setting properties");
return alis;
} catch (Exception e) {
IJError.print(e);
}
return null;
}
Aggregations