def test_basic_2d_affine(): linear_component = np.array([[1, -6], [-3, 2]]) translation_component = np.array([7, -8]) h_matrix = np.eye(3, 3) h_matrix[:-1, :-1] = linear_component h_matrix[:-1, -1] = translation_component affine = Affine(h_matrix) x = np.array([[0, 1], [1, 1], [-1, -5], [3, -5]]) # transform x explicitly solution = np.dot(x, linear_component.T) + translation_component # transform x using the affine transform result = affine.apply(x) # check that both answers are equivalent assert_allclose(solution, result) # create several copies of x x_copies = np.array([x, x, x, x, x, x, x, x]) # transform all of copies at once using the affine transform results = affine.apply(x_copies) # check that all copies have been transformed correctly for r in results: assert_allclose(solution, r)
def skew_shape(pointcloud, theta, phi): r""" Method that skews the provided pointcloud. Parameters ---------- pointcloud : `menpo.shape.PointCloud` The shape to distort. theta : `float` The skew angle over x axis (tan(theta)). phi : `float` The skew angle over y axis (tan(phi)). Returns ------- skewed_shape : `menpo.shape.PointCloud` The skewed (distorted) pointcloud. """ rotate_ccw = Similarity.init_identity(pointcloud.n_dims) # Create skew matrix h_matrix = np.ones((3, 3)) h_matrix[0, 1] = np.tan(theta * np.pi / 180.) h_matrix[1, 0] = np.tan(phi * np.pi / 180.) h_matrix[:2, 2] = 0. h_matrix[2, :2] = 0. r = Affine(h_matrix) t = Translation(-pointcloud.centre(), skip_checks=True) # Translate to origin, rotate counter-clockwise, then translate back rotate_ccw.compose_before_inplace(t) rotate_ccw.compose_before_inplace(r) rotate_ccw.compose_before_inplace(t.pseudoinverse()) return rotate_ccw.apply(pointcloud)
def test_align_2d_affine(): linear_component = np.array([[1, -6], [-3, 2]]) translation_component = np.array([7, -8]) h_matrix = np.eye(3, 3) h_matrix[:-1, :-1] = linear_component h_matrix[:-1, -1] = translation_component affine = Affine(h_matrix) source = PointCloud(np.array([[0, 1], [1, 1], [-1, -5], [3, -5]])) target = affine.apply(source) # estimate the transform from source and target estimate = AlignmentAffine(source, target) # check the estimates is correct assert_allclose(affine.h_matrix, estimate.h_matrix)
def _produce_affine_transforms_per_tri(self): r""" Compute the affine transformation between each triangle in the source and target. This is calculated analytically. """ # we permute the axes of the indexed point set to have shape # [3, n_dims, n_tris] for ease of indexing in. s = np.transpose(self.source.points[self.trilist], axes=[1, 2, 0]) t = np.transpose(self.target.points[self.trilist], axes=[1, 2, 0]) # sik # ^^^ # ||\- the k'th point # || # |vector between end (j or k) and i # source [target] # if i is absent, it is the position of the ijk point. # (not a _vector_ between points) # get vectors ij ik for source and target sij, sik = s[1] - s[0], s[2] - s[0] tij, tik = t[1] - t[0], t[2] - t[0] # source vertex positions si, sj, sk = s[0], s[1], s[2] ti = t[0] d = (sij[0] * sik[1]) - (sij[1] * sik[0]) c_x = (sik[1] * tij - sij[1] * tik) / d c_y = (sij[0] * tik - sik[0] * tij) / d c_t = ti + (tij * (si[1] * sik[0] - si[0] * sik[1]) + tik * (si[0] * sij[1] - si[1] * sij[0])) / d ht = np.repeat(np.eye(3)[..., None], self.n_tris, axis=2) ht[:2, 0] = c_x ht[:2, 1] = c_y ht[:2, 2] = c_t transforms = [] for i in range(self.n_tris): transforms.append(Affine(ht[..., i])) # store our state out self.transforms = transforms self.s, self.t = s, t self.sij, self.sik = sij, sik self.tij, self.tik = tij, tik
def test_affine_3d_n_parameters(): h**o = np.eye(4) t = Affine(h**o) assert(t.n_parameters == 12)
def test_affine_2d_n_dims_output(): h**o = np.eye(3) t = Affine(h**o) assert(t.n_dims_output == 2)
def test_affine_2d_n_parameters(): h**o = np.eye(3) t = Affine(h**o) assert(t.n_parameters == 6)
def test_affine_pseudoinverse(): s = NonUniformScale([4, 3]) inv_man = NonUniformScale([1. / 4, 1. / 3]) b = Affine(s.h_matrix) i = b.pseudoinverse() assert_allclose(i.h_matrix, inv_man.h_matrix)
def test_affine_non_square_h_matrix(): h**o = np.random.rand(4, 6) Affine(h**o)
def test_affine_incorrect_bottom_row(): h**o = np.random.rand(4, 4) Affine(h**o)
def test_affine_non_square_h_matrix(): h**o = np.random.rand(4, 6) with raises(ValueError): Affine(h**o)
def test_affine_incorrect_bottom_row(): h**o = np.random.rand(4, 4) with raises(ValueError): Affine(h**o)