/** * constructor to create a view * * @param projection: projection image as Grid2D * @param radon: radon transformed and derived image as Grid2D * @param projMatrix: projection matrix as Projection */ public View(Grid2D projection, Grid2D radon, Projection projMatrix) { // Initialize center matrix // CENTER = new SimpleMatrix(3, 4); CENTER.setDiagValue(new SimpleVector(1.0, 1.0, 1.0)); // get data out of projection // this.projectionWidth = projection.getWidth(); this.projectionHeight = projection.getHeight(); // get data out of radon transformed image // this.radonWidth = radon.getWidth(); this.radonHeight = radon.getHeight(); this.projectionDiag = Math.sqrt(projectionWidth * projectionWidth + projectionHeight * projectionHeight); this.lineIncrement = radonWidth / projectionDiag; this.angleIncrement = radonHeight / Math.PI; // store radon transformed image // this.radon = radon; // get projection matrix P (3x4) // this.P = SimpleOperators.multiplyMatrixProd(projMatrix.getK(), CENTER); this.P = SimpleOperators.multiplyMatrixProd(this.P, projMatrix.getRt()); // get source position C (nullspace of the projection) // DecompositionSVD decoP = new DecompositionSVD(this.P); this.C = decoP.getV().getCol(3); // normalize source vectors by last component // // it is important that the last component is positive to have a positive center // as it is defined in oriented projective geometry this.C = this.C.dividedBy(this.C.getElement(3)); }
/** * method to calculate a mapping K from two source positions C0, C1 to a plane C0 (C1) is the * source position from the first (second) view */ public void createMappingToEpipolarPlane() { // set up source matrices // SimpleVector C0 = this.view1.C; SimpleVector C1 = this.view2.C; // compute Pluecker coordinates // double L01 = C0.getElement(0) * C1.getElement(1) - C0.getElement(1) * C1.getElement(0); double L02 = C0.getElement(0) * C1.getElement(2) - C0.getElement(2) * C1.getElement(0); double L03 = C0.getElement(0) * C1.getElement(3) - C0.getElement(3) * C1.getElement(0); double L12 = C0.getElement(1) * C1.getElement(2) - C0.getElement(2) * C1.getElement(1); double L13 = C0.getElement(1) * C1.getElement(3) - C0.getElement(3) * C1.getElement(1); double L23 = C0.getElement(2) * C1.getElement(3) - C0.getElement(3) * C1.getElement(2); // construct B (6x1) // SimpleVector B = new SimpleVector(L01, L02, L03, L12, L13, L23); // compute infinity point in direction of B // SimpleVector N = new SimpleVector(-L03, -L13, -L23, 0); // compute plane E0 containing B and X0=(0,0,0,1) // SimpleVector E0 = SimpleOperators.getPlueckerJoin(B, new SimpleVector(0, 0, 0, 1)); // find othonormal basis from plane normals // // (vectors are of 3x1) SimpleVector a2 = new SimpleVector(E0.getElement(0), E0.getElement(1), E0.getElement(2)); SimpleVector a3 = new SimpleVector(N.getElement(0), N.getElement(1), N.getElement(2)); // set vectors to unit length a2.normalizeL2(); a3.normalizeL2(); // calculate cross product to get the last basis vector // SimpleVector a1 = General.crossProduct(a2, a3).negated(); // (a1 is already of unit length -> no normalization needed) // set up assembly matrix A (4x3) // SimpleMatrix A = new SimpleMatrix(4, 3); A.setSubColValue(0, 0, a1); A.setSubColValue(0, 1, a2); A.setSubColValue(0, 2, C0); // store mapping matrix K (4x3 = 4x4 * 4x3) // this.K = SimpleOperators.multiplyMatrixProd(SimpleOperators.getPlueckerMatrixDual(B), A); }