Java源码示例:net.imglib2.RealInterval
示例1
private void setRenderedImageListener()
{
renderUnit.getRenderedImageProperty().addListener((obs, oldv, newv) -> {
if (newv != null && newv.getImage() != null) {
final Interval screenInterval = newv.getScreenInterval();
final RealInterval renderTargetRealInterval = newv.getRenderTargetRealInterval();
canvasPane.getCanvas().getGraphicsContext2D().drawImage(
newv.getImage(), // src
renderTargetRealInterval.realMin(0), // src X
renderTargetRealInterval.realMin(1), // src Y
renderTargetRealInterval.realMax(0) - renderTargetRealInterval.realMin(0), // src width
renderTargetRealInterval.realMax(1) - renderTargetRealInterval.realMin(1), // src height
screenInterval.min(0), // dst X
screenInterval.min(1), // dst Y
screenInterval.dimension(0), // dst width
screenInterval.dimension(1) // dst height
);
}
});
}
示例2
public static FinalRealInterval applyTranslation(RealInterval img, TranslationGet translation, boolean[] ignoreDims){
// get number of dimensions we actually use
int n = 0;
for (int d = 0; d < ignoreDims.length; ++d)
if (!ignoreDims[d])
n++;
final double [] min = new double [n];
final double [] max = new double [n];
int i2 = 0;
for (int i = 0; i< img.numDimensions();++i)
{
if (!ignoreDims[i])
{
min[i2] = img.realMin(i) + translation.getTranslation(i);
max[i2] = img.realMax(i) + translation.getTranslation(i);
i2++;
}
}
return new FinalRealInterval(min, max);
}
示例3
/**
* create an integer interval from real interval, being conservatie on the size
* (min is ceiled, max is floored)
* @param overlap real input
* @return interger interval, with mins ceiled and maxs floored
*/
public static FinalInterval getLocalRasterOverlap(RealInterval overlap)
{
final int n = overlap.numDimensions();
final long [] min = new long [n];
final long [] max = new long [n];
for (int i = 0; i< n; i++)
{
// round down errors when it is exactly 0.5, if we do not do this we end up with two intervals
// of different size, e.g.:
// if the first interval starts at 139.5 going to 199, the second one at 0.0 going to 59.5
// then the rastered 1st would go from round(139.5)=140 + 1 = 141 -to- round(199)=199 - 1 = 198, dim=58
// and the rastered 2nd would go from round(0.0)=0 + 1 = 1 -to- round(59.5)=60 - 1 = 59, dim=59
min[i] = Math.round((overlap.realMin(i) - 0.0001 )) + 1;
max[i] = Math.round((overlap.realMax(i) + 0.0001 )) - 1;
}
return new FinalInterval(min, max);
}
示例4
public static FinalRealInterval getOverlap(final RealInterval img1, final RealInterval img2){
final int n = img1.numDimensions();
final double [] min = new double [n];
final double [] max = new double [n];
for (int i = 0; i< n; i++)
{
min[i] = Math.max(img1.realMin(i), img2.realMin(i));
max[i] = Math.min(img1.realMax(i), img2.realMax(i));
// intervals do not overlap
if ( max[i] < min [i])
return null;
}
return new FinalRealInterval(min, max);
}
示例5
public RenderResult(
final Image image,
final Interval screenInterval,
final RealInterval renderTargetRealInterval,
final int screenScaleIndex) {
this.image = image;
this.screenInterval = screenInterval;
this.renderTargetRealInterval = renderTargetRealInterval;
this.screenScaleIndex = screenScaleIndex;
}
示例6
private RandomAccessibleInterval<UnsignedLongType> getTransformedMaskSection(final SectionInfo sectionInfo)
{
final RealInterval sectionBounds = sectionInfo.sourceToDisplayTransform.estimateBounds(sectionInfo.sourceBoundingBox);
final Interval sectionInterval = Intervals.smallestContainingInterval(sectionBounds);
final RealRandomAccessible<UnsignedLongType> transformedMask = getTransformedMask(sectionInfo.mask, sectionInfo.sourceToDisplayTransform);
final RandomAccessibleInterval<UnsignedLongType> transformedMaskInterval = Views.interval(Views.raster(transformedMask), sectionInterval);
return Views.hyperSlice(transformedMaskInterval, 2, 0l);
}
示例7
private synchronized void paint(final double viewerX, final double viewerY)
{
LOG.debug( "At {} {}", viewerX, viewerY );
if (!this.isPainting) {
LOG.debug("Not currently activated for painting, returning without action");
return;
}
final RandomAccessibleInterval<UnsignedLongType> mask = getMaskIfIsPaintingOrNull();
if (mask == null) {
LOG.debug("Current mask is null, returning without action");
return;
}
final double radius = brushRadius.getAsDouble();
final Interval trackedInterval = Paint2D.paint(
Views.extendValue(mask, new UnsignedLongType(Label.INVALID)),
this.fillLabel,
viewerX,
viewerY,
radius,
brushDepth.getAsDouble(),
labelToViewerTransform,
globalToViewerTransform,
labelToGlobalTransform);
this.interval = this.interval == null
? trackedInterval
: Intervals.union(trackedInterval, this.interval);
++this.fillLabel;
final RealInterval trackedIntervalInGlobalSpace = IntervalHelpers.extendAndTransformBoundingBox(trackedInterval, labelToGlobalTransform, 0.5);
this.paintera.orthogonalViews().requestRepaint(trackedIntervalInGlobalSpace);
}
示例8
public ViewFrustum(final PerspectiveCamera camera, final double[] screenSize)
{
this.screenSize = screenSize.clone();
this.tanHalfFov = new double[2];
final double widthToHeightRatio = screenSize[0] / screenSize[1];
final double halfFovMainDimension = Math.toRadians(camera.getFieldOfView() / 2);
if (camera.isVerticalFieldOfView())
{
tanHalfFov[1] = Math.tan(halfFovMainDimension);
tanHalfFov[0] = tanHalfFov[1] * widthToHeightRatio;
}
else
{
tanHalfFov[0] = Math.tan(halfFovMainDimension);
tanHalfFov[1] = tanHalfFov[0] / widthToHeightRatio;
}
final ViewFrustumPlane[] newNearFarPlanes = new ViewFrustumPlane[2];
final double[] clipValues = {camera.getNearClip(), camera.getFarClip()};
for (int i = 0; i < 2; ++i)
{
final double clipVal = clipValues[i];
final RealInterval viewPlane2D = viewPlaneAtGivenDistance(clipVal);
newNearFarPlanes[i] = new ViewFrustumPlane();
newNearFarPlanes[i].minMin.setPosition(new double[] {viewPlane2D.realMin(0), viewPlane2D.realMin(1), clipVal});
newNearFarPlanes[i].minMax.setPosition(new double[] {viewPlane2D.realMin(0), viewPlane2D.realMax(1), clipVal});
newNearFarPlanes[i].maxMin.setPosition(new double[] {viewPlane2D.realMax(0), viewPlane2D.realMin(1), clipVal});
newNearFarPlanes[i].maxMax.setPosition(new double[] {viewPlane2D.realMax(0), viewPlane2D.realMax(1), clipVal});
}
nearFarPlanes = new ViewFrustumPlanes(
newNearFarPlanes[0],
newNearFarPlanes[1]
);
}
示例9
public RealInterval viewPlaneAtGivenDistance(final double z)
{
final double[] min = new double[2], max = new double[2];
for (int d = 0; d < 2; ++d)
{
final double halfLen = tanHalfFov[d] * z;
min[d] = -halfLen;
max[d] = +halfLen;
}
return new FinalRealInterval(min, max);
}
示例10
@Override
public RealRandomAccessible<T> getInterpolatedSource(final int t, final int level, final Interpolation method)
{
final RealRandomAccessible<T> sourceToExtend;
// ignore interpolation method because we cannot use linear interpolation on LabelMultisetType
final RealRandomAccessible<T> interpolatedSource = this.source.getInterpolatedSource(t, level, Interpolation.NEARESTNEIGHBOR);
if (!this.showCanvasOverBackground.get() || this.affectedBlocks.size() == 0 && this.currentMask == null)
{
LOG.debug("Hide canvas or no mask/canvas data present -- delegate to underlying source");
sourceToExtend = interpolatedSource;
}
else
{
final RealRandomAccessible<VolatileUnsignedLongType> canvas = interpolateNearestNeighbor(Views.extendValue(this.canvases[level].getRai(), new VolatileUnsignedLongType(Label.INVALID)));
final RealRandomAccessible<VolatileUnsignedLongType> mask = this.tMasks[level];
final RealRandomAccessibleTriple<T, VolatileUnsignedLongType, VolatileUnsignedLongType> composed = new
RealRandomAccessibleTriple<>(
interpolatedSource,
canvas,
mask
);
sourceToExtend = new PickOne<>(composed, pacT.copyWithDifferentNumOccurences(numContainedVoxels(level)));
}
// extend the interpolated source with the specified out of bounds value
final RealInterval bounds = new FinalRealInterval(source.getSource(t, level));
final RealRandomAccessibleRealInterval<T> boundedSource = new FinalRealRandomAccessibleRealInterval<>(sourceToExtend, bounds);
return new ExtendedRealRandomAccessibleRealInterval<>(boundedSource, new RealOutOfBoundsConstantValueFactory<>(extensionT.copy()));
}
示例11
@Override
public RealRandomAccessible<D> getInterpolatedDataSource(final int t, final int level, final Interpolation method)
{
final RealRandomAccessible<D> dataSourceToExtend;
// ignore interpolation method because we cannot use linear interpolation on LabelMultisetType
final RealRandomAccessible<D> interpolatedDataSource = this.source.getInterpolatedDataSource(t, level, Interpolation.NEARESTNEIGHBOR);
if (!this.showCanvasOverBackground.get() || this.affectedBlocks.size() == 0 && this.currentMask == null)
{
LOG.debug("Hide canvas or no mask/canvas data present -- delegate to underlying source");
dataSourceToExtend = interpolatedDataSource;
}
else
{
final RealRandomAccessible<UnsignedLongType> dataCanvas = interpolateNearestNeighbor(Views.extendValue(this.dataCanvases[level], new UnsignedLongType(Label.INVALID)));
final RealRandomAccessible<UnsignedLongType> dataMask = this.dMasks[level];
final RealRandomAccessibleTriple<D, UnsignedLongType, UnsignedLongType> composed = new RealRandomAccessibleTriple<>(
interpolatedDataSource,
dataCanvas,
dataMask);
dataSourceToExtend = new PickOne<>(composed, pacD.copyWithDifferentNumOccurences(numContainedVoxels(level)));
}
// extend the interpolated source with the specified out of bounds value
final RealInterval bounds = new FinalRealInterval(source.getDataSource(t, level));
final RealRandomAccessibleRealInterval<D> boundedDataSource = new FinalRealRandomAccessibleRealInterval<>(dataSourceToExtend, bounds);
return new ExtendedRealRandomAccessibleRealInterval<>(boundedDataSource, new RealOutOfBoundsConstantValueFactory<>(extensionD.copy()));
}
示例12
private Node createBlockShape(final ShapeKey<T> key)
{
final Interval keyInterval = key.interval();
final double[] worldMin = new double[3], worldMax = new double[3];
Arrays.setAll(worldMin, d -> keyInterval.min(d));
Arrays.setAll(worldMax, d -> keyInterval.min(d) + keyInterval.dimension(d));
unshiftedWorldTransforms.apply(key.scaleIndex()).apply(worldMin, worldMin);
unshiftedWorldTransforms.apply(key.scaleIndex()).apply(worldMax, worldMax);
final RealInterval blockWorldInterval = new FinalRealInterval(worldMin, worldMax);
final double[] blockWorldSize = new double[blockWorldInterval.numDimensions()];
Arrays.setAll(blockWorldSize, d -> blockWorldInterval.realMax(d) - blockWorldInterval.realMin(d));
// the standard Box primitive is made up of triangles, so the unwanted diagonals are visible when using DrawMode.Line
// final Box box = new Box(
// blockWorldSize[0],
// blockWorldSize[1],
// blockWorldSize[2]
// );
final PolygonMeshView box = new PolygonMeshView(Meshes.createQuadrilateralMesh(
(float) blockWorldSize[0],
(float) blockWorldSize[1],
(float) blockWorldSize[2]
));
final double[] blockWorldTranslation = new double[blockWorldInterval.numDimensions()];
Arrays.setAll(blockWorldTranslation, d -> blockWorldInterval.realMin(d) + blockWorldSize[d] * 0.5);
box.setTranslateX(blockWorldTranslation[0]);
box.setTranslateY(blockWorldTranslation[1]);
box.setTranslateZ(blockWorldTranslation[2]);
final PhongMaterial material = Meshes.painteraPhongMaterial();
box.setCullFace(CullFace.NONE);
box.setMaterial(material);
box.setDrawMode(DrawMode.LINE);
return box;
}
示例13
/**
* Get all blocks/cells of a {@link CellGrid} that the real interval defined by {@code min} and {@code max}
* intersects with, represented as linear indices.
* @param interval interval
* @param cellGrid defines grid (block size/cell size)
* @return linear indices of all cells/blocks that intersect with interval defined by {@code min}, {@code max}.
*/
public static long[] getIntersectingBlocks(
final RealInterval interval,
final CellGrid cellGrid)
{
return getIntersectingBlocks(
Intervals.minAsDoubleArray(interval),
Intervals.maxAsDoubleArray(interval),
cellGrid
);
}
示例14
public < F extends RealInterval & RealRandomAccessible< T > > AbstractRealOutOfBoundsValue( final F f )
{
super( f.numDimensions() );
this.sampler = f.realRandomAccess();
min = new double[ n ];
f.realMin( min );
max = new double[ n ];
f.realMax( max );
dimIsOutOfBounds = new boolean[ n ];
}
示例15
/**
* get overlap in local image coordinates (assuming min = (0,0,..))
* @param img image interval (global coordinates)
* @param overlap overlap interval (global coordinates)
* @return overlap interval in local coordinates
*/
public static FinalRealInterval getLocalOverlap(RealInterval img, RealInterval overlap){
final int n = img.numDimensions();
final double [] min = new double [n];
final double [] max = new double [n];
for (int i = 0; i< n; i++)
{
min[i] = Math.max(0, overlap.realMin(i) - img.realMin(i)) ;
max[i] = Math.max(0, overlap.realMax(i) - img.realMin(i));
}
return new FinalRealInterval(min, max);
}
示例16
@Override
public RealRandomAccess<FloatType> realRandomAccess( final RealInterval interval )
{
return Views.interpolate(
Views.extendZero( this.contentBasedImg ),
new NLinearInterpolatorFactory< FloatType >()
).realRandomAccess( interval );
}
示例17
@Override
public void paint()
{
final List<SourceAndConverter<?>> sacs = new ArrayList<>();
final AffineTransform3D viewerTransform = new AffineTransform3D();
final int timepoint;
synchronized (RenderUnit.this)
{
if (renderer != null && renderTarget != null)
{
final ViewerState viewerState = RenderUnit.this.viewerState.get();
synchronized (viewerState)
{
viewerState.getViewerTransform(viewerTransform);
timepoint = viewerState.getTimepoint();
sacs.addAll(viewerState.getSources());
}
}
else
{
return;
}
}
final int renderedScreenScaleIndex = renderer.paint(
sacs,
timepoint,
viewerTransform,
interpolation,
null
);
if (renderedScreenScaleIndex != -1)
{
final Interval screenInterval = renderer.getLastRenderedScreenInterval();
final RealInterval renderTargetRealInterval = renderer.getLastRenderTargetRealInterval();
renderTarget.drawOverlays(img -> renderResultProperty.set(new RenderResult(
img,
screenInterval,
renderTargetRealInterval,
renderedScreenScaleIndex
)));
}
}
示例18
public RealInterval getRenderTargetRealInterval() {
return renderTargetRealInterval;
}
示例19
public synchronized RealInterval getLastRenderTargetRealInterval()
{
return lastRenderTargetRealInterval;
}
示例20
public void requestRepaint(final RealInterval intervalInGlobalSpace)
{
this.applyToAll(v -> v.requestRepaint(intervalInGlobalSpace));
}
示例21
@Override
public AbstractConvertedRealRandomAccess<Triple<A, B, C>, D> realRandomAccess(final RealInterval interval)
{
return realRandomAccess();
}
示例22
@Override
public RealRandomAccess realRandomAccess(final RealInterval interval)
{
return new RealRandomAccess();
}
示例23
public < F extends RealInterval & RealRandomAccessible< T > > RealOutOfBoundsConstantValue( final F f, final T value )
{
super( f );
this.value = value;
}
示例24
public static void main(String[] args)
{
RandomAccessibleInterval< FloatType > a = ImgLib2Util.openAs32Bit( new File( "73.tif.zip" ) );
RandomAccessibleInterval< FloatType > b = ImgLib2Util.openAs32Bit( new File( "74.tif.zip" ) );
long slice = 40;
ImageJFunctions.show( a );
a = Views.zeroMin( Views.hyperSlice( a, 2, slice ));
b = Views.zeroMin( Views.hyperSlice( b, 2, slice ));
TranslationGet t1 = new Translation2D();
TranslationGet t2 = new Translation2D(460, 0);
ArrayList< Pair< RealInterval, AffineGet > > views = new ArrayList<Pair<RealInterval, AffineGet>>();
views.add( new ValuePair< RealInterval, AffineGet >( a, t1 ) );
views.add( new ValuePair< RealInterval, AffineGet >( b, t2 ) );
RealInterval overlap = BoundingBoxMaximalGroupOverlap.getMinBoundingIntervalSingle( views );
final RealInterval transformed1 = TransformTools.applyTranslation( a, t1, new boolean[] {false, false} );
final RealInterval transformed2 = TransformTools.applyTranslation( b, t2, new boolean[] {false, false} );
// get overlap in images' coordinates
final RealInterval localOverlap1 = TransformTools.getLocalOverlap( transformed1, overlap );
final RealInterval localOverlap2 = TransformTools.getLocalOverlap( transformed2, overlap );
// round to integer interval
final Interval interval1 = TransformTools.getLocalRasterOverlap( localOverlap1 );
final Interval interval2 = TransformTools.getLocalRasterOverlap( localOverlap2 );
//final WarpFunction warp = new TranslationWarp(3);
final WarpFunction warp = new RigidWarp(2);
//final WarpFunction warp = new AffineWarp( 3 );
// rotate second image
AffineTransform2D rot = new AffineTransform2D();
rot.rotate( 1.4 * Math.PI / 180 );
RandomAccessibleInterval< FloatType > rotated = Views.interval(
RealViews.affine(
Views.interpolate( Views.extendMirrorSingle( Views.zeroMin( Views.interval( b, interval2 ) ) ), new NLinearInterpolatorFactory<>() ),
rot.copy() ),
interval2);
// show input
new ImageJ();
ImageJFunctions.show( Views.interval( a, interval1 ) );
ImageJFunctions.show( rotated );
// downsample input
RandomAccessibleInterval< FloatType > simple2x1 = Downsample.simple2x( Views.zeroMin( Views.interval( a, interval1 ) ), new ArrayImgFactory<>(), new boolean[] {false, false} );
RandomAccessibleInterval< FloatType > simple2x2 = Downsample.simple2x( Views.zeroMin( Views.interval( rotated, interval2 ) ), new ArrayImgFactory<>(), new boolean[] {false, false} );
// align
//Align< FloatType > lk = new Align<>( Views.zeroMin( Views.interval( a, interval1 ) ), new ArrayImgFactory<>(), warp );
Align< FloatType > lk = new Align<>( simple2x1, new ArrayImgFactory<>(), warp );
//System.out.println( Util.printCoordinates( lk.align( Views.zeroMin( Views.interval( b, interval2 ) ), 100, 0.01 ).getRowPackedCopy() ) );
//final AffineTransform transform = lk.align( Views.zeroMin( rotated ), 100, 0.01 );
final AffineTransform transform = lk.align( simple2x2, 100, 0.1 );
// transformation matrix
System.out.println( Util.printCoordinates( transform.getRowPackedCopy() ) );
// correct input and show
RandomAccessibleInterval< FloatType > backRotated = Views.interval(
RealViews.affine(
Views.interpolate( Views.extendMirrorSingle( Views.zeroMin( Views.interval( b, interval2 ) ) ), new NLinearInterpolatorFactory<>() ),
rot.copy().preConcatenate( transform ).copy() ),
interval2);
ImageJFunctions.show( backRotated );
// constructor needs column packed matrix, therefore the transpose
Matrix mt = new Matrix( transform.getRowPackedCopy(), 3).transpose();
Matrix rigid = mt.getMatrix( 0, 1, 0, 1 );
// check whether result is rotation matrix (det == +-1, orthogonal)
System.out.println( rigid.det() );
System.out.println( Util.printCoordinates( rigid.times( rigid.transpose() ).getRowPackedCopy() ) );
}
示例25
public static void main(String[] args)
{
Img< FloatType > a = ImgLib2Util.openAs32Bit( new File( "73.tif.zip" ) );
Img< FloatType > b = ImgLib2Util.openAs32Bit( new File( "74.tif.zip" ) );
TranslationGet t1 = new Translation3D();
TranslationGet t2 = new Translation3D(460, 0, 0);
ArrayList< Pair< RealInterval, AffineGet > > views = new ArrayList<Pair<RealInterval, AffineGet>>();
views.add( new ValuePair< RealInterval, AffineGet >( a, t1 ) );
views.add( new ValuePair< RealInterval, AffineGet >( b, t2 ) );
RealInterval overlap = BoundingBoxMaximalGroupOverlap.getMinBoundingIntervalSingle( views );
final RealInterval transformed1 = TransformTools.applyTranslation( a, t1, new boolean[] {false, false, false} );
final RealInterval transformed2 = TransformTools.applyTranslation( b, t2, new boolean[] {false, false, false} );
// get overlap in images' coordinates
final RealInterval localOverlap1 = TransformTools.getLocalOverlap( transformed1, overlap );
final RealInterval localOverlap2 = TransformTools.getLocalOverlap( transformed2, overlap );
// round to integer interval
final Interval interval1 = TransformTools.getLocalRasterOverlap( localOverlap1 );
final Interval interval2 = TransformTools.getLocalRasterOverlap( localOverlap2 );
//final WarpFunction warp = new TranslationWarp(3);
final WarpFunction warp = new RigidWarp(3);
//final WarpFunction warp = new AffineWarp( 3 );
// rotate second image
AffineTransform3D rot = new AffineTransform3D();
rot.rotate( 2, 2 * Math.PI / 180 );
RandomAccessibleInterval< FloatType > rotated = Views.interval(
RealViews.affine(
Views.interpolate( Views.extendBorder( Views.zeroMin( Views.interval( b, interval2 ) ) ), new NLinearInterpolatorFactory<>() ),
rot.copy() ),
interval2);
// show input
new ImageJ();
ImageJFunctions.show( Views.interval( a, interval1 ), "target" );
ImageJFunctions.show( rotated, "in");
// downsample input
RandomAccessibleInterval< FloatType > simple2x1 = Downsample.simple2x( Views.zeroMin( Views.interval( a, interval1 ) ), new ArrayImgFactory<>(), new boolean[] {true, true, false} );
RandomAccessibleInterval< FloatType > simple2x2 = Downsample.simple2x( Views.zeroMin( Views.interval( rotated, interval2 ) ), new ArrayImgFactory<>(), new boolean[] {true, true, false} );
// align
//Align< FloatType > lk = new Align<>( Views.zeroMin( Views.interval( a, interval1 ) ), new ArrayImgFactory<>(), warp );
Align< FloatType > lk = new Align<>( simple2x1, new ArrayImgFactory<>(), warp );
//System.out.println( Util.printCoordinates( lk.align( Views.zeroMin( Views.interval( b, interval2 ) ), 100, 0.01 ).getRowPackedCopy() ) );
//final AffineTransform transform = lk.align( Views.zeroMin( rotated ), 100, 0.01 );
final AffineTransform transform = lk.align( simple2x2, 100, 0.01 );
final AffineTransform scale = new AffineTransform( 3 );
scale.set( 2, 0, 0 );
scale.set( 1, 1, 1 );
transform.preConcatenate( scale );
// transformation matrix
System.out.println( Util.printCoordinates( transform.getRowPackedCopy() ) );
// correct input and show
RandomAccessibleInterval< FloatType > backRotated = Views.interval(
RealViews.affine(
Views.interpolate( Views.extendBorder( Views.zeroMin( Views.interval( b, interval2 ) ) ), new NLinearInterpolatorFactory<>() ),
rot.copy().preConcatenate( transform ).copy() ),
interval2);
ImageJFunctions.show( backRotated, "out" );
// constructor needs column packed matrix, therefore the transpose
Matrix mt = new Matrix( transform.getRowPackedCopy(), 4).transpose();
Matrix rigid = mt.getMatrix( 0, 2, 0, 2 );
// check whether result is rotation matrix (det == +-1, orthogonal)
System.out.println( rigid.det() );
System.out.println( Util.printCoordinates( rigid.times( rigid.transpose() ).getRowPackedCopy() ) );
}
示例26
public static < T extends RealType< T > > Pair<Pair< AffineGet, Double >, RealInterval> computeStitchingNonEqualTransformations(
final Group<? extends ViewId> viewIdsA,
final Group<? extends ViewId> viewIdsB,
final ViewRegistrations vrs,
final PairwiseStitchingParameters params,
final AbstractSequenceDescription< ?,? extends BasicViewDescription<?>, ? > sd,
final GroupedViewAggregator gva,
final long[] downsampleFactors,
final ExecutorService service )
{
final double[] downsampleDbl = new double[downsampleFactors.length];
for (int d = 0; d < downsampleFactors.length; d++)
downsampleDbl[d] = downsampleFactors[d];
// get Overlap Bounding Box
final List<List<ViewId>> views = new ArrayList<>();
views.add( new ArrayList<>(viewIdsA.getViews()) );
views.add( new ArrayList<>(viewIdsB.getViews()) );
BoundingBoxMaximalGroupOverlap< ViewId > bbDet = new BoundingBoxMaximalGroupOverlap<ViewId>( views, sd, vrs );
BoundingBox bbOverlap = bbDet.estimate( "Max Overlap" );
// we could not find overlap -> ignore this pair
if (bbOverlap == null)
return null;
List<RandomAccessibleInterval< FloatType >> raiOverlaps = new ArrayList<>();
for (List< ViewId > tileViews : views)
{
// wrap every view id (corresponding e.g. to different channels, illums,.. ) in list
List<List< ViewId >> wrapped = tileViews.stream().map( v -> {
ArrayList< ViewId > wrp = new ArrayList<ViewId>();
wrp.add( v );
return wrp;} ).collect( Collectors.toList() );
// open all of them "virtually fused"
List< RandomAccessibleInterval< FloatType > > openFused =
DisplayOverlapTestPopup.openVirtuallyFused( sd, vrs, wrapped, bbOverlap, downsampleDbl );
// aggregate the group into one image
RandomAccessibleInterval< FloatType > raiI = gva.aggregate(
openFused,
tileViews,
sd );
raiOverlaps.add(raiI);
}
// the overlap in both images
final RandomAccessibleInterval< FloatType > img1 = raiOverlaps.get(0);
final RandomAccessibleInterval< FloatType > img2 = raiOverlaps.get(1);
// compute phase correlation shift (passing (0,0,..) translations prevents any overlap correction inside)
final Pair< Translation, Double > result = PairwiseStitching.getShift(
img1,
img2,
new Translation( img1.numDimensions() ),
new Translation( img1.numDimensions() ),
params,
service );
if (result == null)
return null;
for (int i = 0; i< result.getA().numDimensions(); ++i)
result.getA().set( result.getA().get(i, result.getA().numDimensions()) * downsampleFactors[i], i );
// TODO (?): Different translational part of downsample Transformations should be considered via TransformTools.getInitialTransforms
// we probalbly do not have to correct for them ?
final AffineTransform3D vr = vrs.getViewRegistration(viewIdsB.iterator().next()).getModel();
final AffineTransform resCorrected = new AffineTransform( result.getA().numDimensions() );
resCorrected.set( result.getA() );
System.out.println("shift: " + Util.printCoordinates(result.getA().getTranslationCopy()));
System.out.print("cross-corr: " + result.getB());
return new ValuePair<>( new ValuePair<>( resCorrected, result.getB() ), bbOverlap );
}
示例27
public static < T extends RealType< T > > Pair<Pair< AffineGet, Double >, RealInterval> computeStitchingNonEqualTransformationsLucasKanade(
final Group<? extends ViewId> viewIdsA,
final Group<? extends ViewId> viewIdsB,
final ViewRegistrations vrs,
final LucasKanadeParameters params,
final AbstractSequenceDescription< ?,? extends BasicViewDescription<?>, ? > sd,
final GroupedViewAggregator gva,
final long[] downsampleFactors,
final ExecutorService service )
{
final double[] downsampleDbl = new double[downsampleFactors.length];
for (int d = 0; d < downsampleFactors.length; d++)
downsampleDbl[d] = downsampleFactors[d];
// get Overlap Bounding Box
final List<List<ViewId>> views = new ArrayList<>();
views.add( new ArrayList<>(viewIdsA.getViews()) );
views.add( new ArrayList<>(viewIdsB.getViews()) );
BoundingBoxMaximalGroupOverlap< ViewId > bbDet = new BoundingBoxMaximalGroupOverlap<ViewId>( views, sd, vrs );
BoundingBox bbOverlap = bbDet.estimate( "Max Overlap" );
// we could not find overlap -> ignore this pair
if (bbOverlap == null)
return null;
List<RandomAccessibleInterval< FloatType >> raiOverlaps = new ArrayList<>();
for (List< ViewId > tileViews : views)
{
// wrap every view id (corresponding e.g. to different channels, illums,.. ) in list
List<List< ViewId >> wrapped = tileViews.stream().map( v -> {
ArrayList< ViewId > wrp = new ArrayList<ViewId>();
wrp.add( v );
return wrp;} ).collect( Collectors.toList() );
// open all of them "virtually fused"
List< RandomAccessibleInterval< FloatType > > openFused =
DisplayOverlapTestPopup.openVirtuallyFused( sd, vrs, wrapped, bbOverlap, downsampleDbl );
// aggregate the group into one image
RandomAccessibleInterval< FloatType > raiI = gva.aggregate(
openFused,
tileViews,
sd );
raiOverlaps.add(raiI);
}
// the overlap in both images
final RandomAccessibleInterval< FloatType > img1 = raiOverlaps.get(0);
final RandomAccessibleInterval< FloatType > img2 = raiOverlaps.get(1);
// compute phase correlation shift (passing (0,0,..) translations prevents any overlap correction inside)
final Pair< AffineTransform, Double > result = PairwiseStitching.getShiftLucasKanade(
img1,
img2,
new Translation( img1.numDimensions() ),
new Translation( img1.numDimensions() ),
params,
service );
if (result == null)
return null;
// scale just the translational part
for (int i = 0; i< result.getA().numDimensions(); ++i)
result.getA().set( result.getA().get(i, result.getA().numDimensions()) * downsampleFactors[i], i );
// TODO (?): Different translational part of downsample Transformations should be considered via TransformTools.getInitialTransforms
// we probalbly do not have to correct for them ?
final AffineTransform3D vr = vrs.getViewRegistration(viewIdsB.iterator().next()).getModel();
final AffineTransform resCorrected = new AffineTransform( result.getA().numDimensions() );
resCorrected.set( result.getA() );
IOFunctions.println("resulting transformation: " + Util.printCoordinates(result.getA().getRowPackedCopy()));
return new ValuePair<>( new ValuePair<>( resCorrected, result.getB() ), bbOverlap );
}
示例28
public static < T extends RealType< T > > Pair<Pair< AffineGet, Double >, RealInterval> computeStitching(
final Group<? extends ViewId> viewIdsA,
final Group<? extends ViewId> viewIdsB,
final ViewRegistrations vrs,
final PairwiseStitchingParameters params,
final AbstractSequenceDescription< ?,? extends BasicViewDescription<?>, ? > sd,
final GroupedViewAggregator gva,
final long[] downsampleFactors,
final ExecutorService service )
{
// the transformation that maps the downsampled image coordinates back to the original input(!) image space
final AffineTransform3D dsCorrectionT1 = new AffineTransform3D();
final AffineTransform3D dsCorrectionT2 = new AffineTransform3D();
// get Overlap Bounding Box
final List<List<ViewId>> views = new ArrayList<>();
views.add( new ArrayList<>(viewIdsA.getViews()) );
views.add( new ArrayList<>(viewIdsB.getViews()) );
BoundingBoxMaximalGroupOverlap< ViewId > bbDet = new BoundingBoxMaximalGroupOverlap<ViewId>( views, sd, vrs );
BoundingBox bbOverlap = bbDet.estimate( "Max Overlap" );
// this should be caught outside of this method already, but check nonetheless
if (bbOverlap == null)
return null;
// get one image per group
final RandomAccessibleInterval<T> img1 = gva.aggregate( viewIdsA, sd, downsampleFactors, dsCorrectionT1 );
final RandomAccessibleInterval<T> img2 = gva.aggregate( viewIdsB, sd, downsampleFactors, dsCorrectionT2 );
if (img1 == null || img2 == null)
{
IOFunctions.println( "WARNING: Tried to open missing View when computing Stitching for " + viewIdsA + " and " +
viewIdsB + ". No link between those could be determined");
return null;
}
// get translations
// TODO: is the 2d check here meaningful?
// everything will probably be 3d at this point, since ImgLoaders return 3d images
boolean is2d = img1.numDimensions() == 2;
Pair< AffineGet, TranslationGet > t1 = TransformTools.getInitialTransforms( vrs.getViewRegistration(viewIdsA.iterator().next()), is2d, dsCorrectionT1 );
Pair< AffineGet, TranslationGet > t2 = TransformTools.getInitialTransforms( vrs.getViewRegistration(viewIdsB.iterator().next()), is2d, dsCorrectionT2 );
final Pair< Translation, Double > result = PairwiseStitching.getShift( img1, img2, t1.getB(), t2.getB(), params, service );
if (result == null)
return null;
for (int i = 0; i< result.getA().numDimensions(); ++i)
result.getA().set( result.getA().get(i, result.getA().numDimensions()) * downsampleFactors[i], i );
// TODO (?): Different translational part of downsample Transformations should be considered via TransformTools.getInitialTransforms
// we probalbly do not have to correct for them ?
// NB: as we will deal in global coordinates, not pixel coordinates in global optimization,
// calculate global R' = VT^-1 * R * VT from pixel transformation R
ViewRegistration vrOld = vrs.getViewRegistration(viewIdsB.iterator().next());
AffineTransform3D resTransform = new AffineTransform3D();
resTransform.set( result.getA().getRowPackedCopy() );
resTransform.concatenate( vrOld.getModel().inverse() );
resTransform.preConcatenate( vrOld.getModel() );
System.out.println("shift (pixel coordinates): " + Util.printCoordinates(result.getA().getTranslationCopy()));
System.out.println("shift (global coordinates): " + Util.printCoordinates(resTransform.getRowPackedCopy()));
System.out.print("cross-corr: " + result.getB());
return new ValuePair<>( new ValuePair<>( resTransform, result.getB() ), bbOverlap );
}
示例29
public static < T extends RealType< T > > Pair<Pair< AffineGet, Double >, RealInterval> computeStitchingLucasKanade(
final Group<? extends ViewId> viewIdsA,
final Group<? extends ViewId> viewIdsB,
final ViewRegistrations vrs,
final LucasKanadeParameters params,
final AbstractSequenceDescription< ?,? extends BasicViewDescription<?>, ? > sd,
final GroupedViewAggregator gva,
final long[] downsampleFactors,
final ExecutorService service )
{
// the transformation that maps the downsampled image coordinates back to the original input(!) image space
final AffineTransform3D dsCorrectionT1 = new AffineTransform3D();
final AffineTransform3D dsCorrectionT2 = new AffineTransform3D();
// get Overlap Bounding Box
final List<List<ViewId>> views = new ArrayList<>();
views.add( new ArrayList<>(viewIdsA.getViews()) );
views.add( new ArrayList<>(viewIdsB.getViews()) );
BoundingBoxMaximalGroupOverlap< ViewId > bbDet = new BoundingBoxMaximalGroupOverlap<ViewId>( views, sd, vrs );
BoundingBox bbOverlap = bbDet.estimate( "Max Overlap" );
// this should be caught outside of this method already, but check nonetheless
if (bbOverlap == null)
return null;
// get one image per group
final RandomAccessibleInterval<T> img1 = gva.aggregate( viewIdsA, sd, downsampleFactors, dsCorrectionT1 );
final RandomAccessibleInterval<T> img2 = gva.aggregate( viewIdsB, sd, downsampleFactors, dsCorrectionT2 );
if (img1 == null || img2 == null)
{
IOFunctions.println( "WARNING: Tried to open missing View when computing Stitching for " + viewIdsA + " and " +
viewIdsB + ". No link between those could be determined");
return null;
}
// get translations
// TODO: is the 2d check here meaningful?
boolean is2d = img1.numDimensions() == 2;
Pair< AffineGet, TranslationGet > t1 = TransformTools.getInitialTransforms( vrs.getViewRegistration(viewIdsA.iterator().next()), is2d, dsCorrectionT1 );
Pair< AffineGet, TranslationGet > t2 = TransformTools.getInitialTransforms( vrs.getViewRegistration(viewIdsB.iterator().next()), is2d, dsCorrectionT2 );
final Pair< AffineTransform, Double > result = PairwiseStitching.getShiftLucasKanade( img1, img2, t1.getB(), t2.getB(), params, service );
if (result == null)
return null;
// TODO: is scaling just the translational part okay here?
for (int i = 0; i< result.getA().numDimensions(); ++i)
result.getA().set( result.getA().get(i, result.getA().numDimensions()) * downsampleFactors[i], i, result.getA().numDimensions() );
// TODO (?): Different translational part of downsample Transformations should be considered via TransformTools.getInitialTransforms
// we probalbly do not have to correct for them ?
// NB: as we will deal in global coordinates, not pixel coordinates in global optimization,
// calculate global R' = VT^-1 * R * VT from pixel transformation R
ViewRegistration vrOld = vrs.getViewRegistration(viewIdsB.iterator().next());
AffineTransform3D resTransform = new AffineTransform3D();
resTransform.set( result.getA().getRowPackedCopy() );
resTransform.concatenate( vrOld.getModel().inverse() );
resTransform.preConcatenate( vrOld.getModel() );
IOFunctions.println("resulting transformation (pixel coordinates): " + Util.printCoordinates(result.getA().getRowPackedCopy()));
IOFunctions.println("resulting transformation (global coordinates): " + Util.printCoordinates(resTransform.getRowPackedCopy()));
return new ValuePair<>( new ValuePair<>( resTransform, result.getB() ), bbOverlap );
}
示例30
@Override
public JuliaRealRandomAccess realRandomAccess( final RealInterval interval )
{
return realRandomAccess();
}