def test_intersection(self): # Create cell. structure = Cell() structure.add_atom(Atom([0, 0, 0], 0)) # Create cell for atom1. cell = VoronoiCell(structure.get_atom(0), radical=True) # Make sure direct faces match up with expectations. neighboring_faces = [] neighboring_faces.append(AtomImage(structure.get_atom(0), [1, 0, 0])) neighboring_faces.append(AtomImage(structure.get_atom(0), [-1, 0, 0])) neighboring_faces.append(AtomImage(structure.get_atom(0), [0, 1, 0])) neighboring_faces.append(AtomImage(structure.get_atom(0), [0, -1, 0])) neighboring_faces.append(AtomImage(structure.get_atom(0), [0, 0, 2])) neighboring_faces.append(AtomImage(structure.get_atom(0), [0, 0, -1])) # Assemble cell. cell.compute_cell_helper(neighboring_faces) # Perform cut. cut_face = VoronoiFace(cell.get_atom(), AtomImage(cell.get_atom(), [0, 0, 1]), radical=True) cell.compute_intersection(cut_face) # Check results. self.assertTrue(cut_face.is_closed()) self.assertEqual(4, cut_face.n_edges()) self.assertTrue(cell.geometry_is_valid()) self.assertEqual(6, cell.n_faces()) self.assertAlmostEqual(1.0, cell.get_volume(), delta=1e-6)
def test_vertex_replacement(self): # Create cell. structure = Cell() structure.add_atom(Atom([0, 0, 0], 0)) # Create cell for atom1. cell = VoronoiCell(structure.get_atom(0), radical=True) # Compute faces. images = [ AtomImage(structure.get_atom(0), sc) for sc in VectorCombinationComputer( structure.get_lattice_vectors(), 1.1).get_supercell_coordinates() ] cell.compute_cell_helper(images) # Make sure it turned out OK. self.assertAlmostEqual(1.0, cell.get_volume(), delta=1e-6) # Find position of atom that will take corner off. p = Plane(p1=(0.4, 0.5, 0.5), p2=(0.5, 0.4, 0.5), p3=(0.5, 0.5, 0.4), tolerance=1e-6) atm_pos = p.project([0, 0, 0]) atm_pos *= 2 structure.add_atom(Atom(atm_pos, 0)) # Cut off the corner. cell.compute_intersection( VoronoiFace(cell.get_atom(), AtomImage(structure.get_atom(1), [0, 0, 0]), radical=False)) vol = cell.get_volume() self.assertEqual(7, cell.n_faces()) # Compute a cell that will cut off just slightly more area. p = Plane(p1=(0.4, 0.5, 0.5), p2=(0.5, 0.35, 0.5), p3=(0.5, 0.5, 0.35), tolerance=1e-6) atm_pos = p.project([0, 0, 0]) atm_pos *= 2 structure.add_atom(Atom(atm_pos, 0)) new_face = VoronoiFace(cell.get_atom(), AtomImage(structure.get_atom(2), [0, 0, 0]), radical=False) self.assertTrue(cell.compute_intersection(new_face)) self.assertEqual(7, cell.n_faces()) self.assertTrue(cell.get_volume() < vol) self.assertTrue(cell.geometry_is_valid()) # Remove that face. cell.remove_face(new_face) self.assertEqual(6, cell.n_faces()) self.assertEqual(6, cell.get_polyhedron_shape()[4]) self.assertAlmostEqual(1.0, cell.get_volume(), delta=1e-6) self.assertTrue(cell.geometry_is_valid())
def test_equals(self): # Make other cell other = Cell() # First check. self.assertTrue(self.cell.__eq__(other)) # Adjust basis. self.cell.set_basis(lengths=[1, 2, 3], angles=[70, 80, 90]) self.assertFalse(self.cell.__eq__(other)) other.set_basis(lengths=[1, 2, 3], angles=[70, 80, 90]) self.assertTrue(self.cell.__eq__(other)) # Add an atom to 0,0,0 self.cell.add_atom(Atom([0, 0, 0], 0)) self.assertFalse(self.cell.__eq__(other)) other.add_atom(Atom([0, 0, 0], 0)) self.assertTrue(self.cell.__eq__(other)) # Changing names. self.cell.set_type_name(0, "Al") self.assertFalse(self.cell.__eq__(other)) other.set_type_name(0, "Al") self.assertTrue(self.cell.__eq__(other)) # Adding more atoms of different type. self.cell.add_atom(Atom([0.5, 0.5, 0], 1)) other.add_atom(Atom([0.5, 0.5, 0], 0)) self.assertFalse(self.cell.__eq__(other)) other.get_atom(1).set_type(1) self.assertTrue(self.cell.__eq__(other)) # Adding atoms with different positions. self.cell.add_atom(Atom([0.5, 0, 0.5], 1)) other.add_atom(Atom([0, 0.5, 0.5], 1)) self.assertFalse(self.cell.__eq__(other)) # Adding atoms out of sequence. other.add_atom(Atom([0.5, 0, 0.5], 1)) self.cell.add_atom(Atom([0, 0.5, 0.5], 1)) self.assertTrue(self.cell.__eq__(other))
def test_creation(self): # Make a simple crystal. cell = Cell() cell.add_atom(Atom([0, 0, 0], 0)) # Initialize faces. image = AtomImage(cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(cell.get_atom(0), image, radical=True) image = AtomImage(cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(cell.get_atom(0), image, radical=True) image = AtomImage(cell.get_atom(0), [1, 0, 0]) face3 = VoronoiFace(cell.get_atom(0), image, radical=True) # Create edges. edge1 = VoronoiEdge(face1, face2) edge2 = VoronoiEdge(face1, face3) # Create vertex. vertex = VoronoiVertex(edge1=edge1, edge2=edge2) # Test properties. self.assertEqual(edge2, vertex.get_previous_edge()) self.assertEqual(edge1, vertex.get_next_edge()) # Make sure the order of edges on creation doesn't matter. self.assertEqual(vertex, VoronoiVertex(edge1=edge2, edge2=edge1)) # Create a new vertex, ensure that it is different. edge3 = VoronoiEdge(face2, face3) self.assertFalse(vertex.__eq__(VoronoiVertex(edge1=edge3, edge2=edge2)))
class testVoronoiEdge(unittest.TestCase): def setUp(self): # Make a simple crystal. self.cell = Cell() self.cell.add_atom(Atom([0, 0, 0], 0)) def tearDown(self): self.cell = None def test_initialize(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edge. edge = VoronoiEdge(face1, face2) # Check out properties. np_tst.assert_array_almost_equal([-1, 0, 0], edge.get_line().get_direction()) def test_is_next(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [1, 0, 0]) face3 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edges. edge1 = VoronoiEdge(face1, face2) edge2 = VoronoiEdge(face1, face3) # Check proper ordering. self.assertTrue(edge2.is_ccw(edge2=edge1)) self.assertFalse(edge1.is_ccw(edge2=edge2)) self.assertFalse(edge2.is_ccw(edge2=edge2)) def test_simple_intersection(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [1, 0, 0]) face3 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [2, 0, 0]) face4 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [-1, 0, 0]) face5 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edges. edge1 = VoronoiEdge(face1, face2) edge2 = VoronoiEdge(face1, face3) edge3 = VoronoiEdge(face1, face4) edge4 = VoronoiEdge(face1, face5) # Compute intersection. self.assertTrue(VoronoiEdge.compute_intersection(edge1, edge3)) self.assertTrue(VoronoiEdge.compute_intersection(edge1, edge2)) self.assertTrue(VoronoiEdge.compute_intersection(edge1, edge4)) # Test properties. np_tst.assert_array_almost_equal( [0.5, 0.5, 0.5], edge1.get_start_vertex().get_position()) np_tst.assert_array_almost_equal([0.5, 0.5, 0.5], edge2.get_end_vertex().get_position()) self.assertAlmostEqual(1.0, edge1.get_length(), delta=1e-6) # Compute intersection that shouldn't happen. self.assertFalse(VoronoiEdge.compute_intersection(edge1, edge3)) def test_join(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [1, 0, 0]) face3 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [2, 0, 0]) face4 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edges. edge1 = VoronoiEdge(face1, face2) edge2 = VoronoiEdge(face1, face3) edge3 = VoronoiEdge(face1, face4) # Join edge1 & edge2. VoronoiEdge.compute_intersection(edge1, edge2, just_join=True) np_tst.assert_array_almost_equal( [0.5, 0.5, 0.5], edge1.get_start_vertex().get_position()) self.assertEqual(edge2, edge1.get_previous_edge()) # Join edge1 & edge3. VoronoiEdge.compute_intersection(edge1, edge3, just_join=True) np_tst.assert_array_almost_equal( [1.0, 0.5, 0.5], edge1.get_start_vertex().get_position()) self.assertEqual(edge3, edge1.get_previous_edge()) def test_compare(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [1, 0, 0]) face3 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edges. edge1 = VoronoiEdge(face1, face2) edge2 = VoronoiEdge(face1, face3) # Tests. self.assertEqual(0, edge1.__cmp__(edge1)) self.assertTrue(edge1.__cmp__(edge2) != 0) self.assertTrue(edge1.__cmp__(edge2) == -1 * edge2.__cmp__(edge1)) self.assertFalse(edge1.__eq__(edge2)) self.assertTrue(edge1.__eq__(edge1)) def test_next_edge(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [-1, 1, 0]) face3 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [-1, 0, 0]) face4 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edges. edge1 = VoronoiEdge(face1, face2) edge2 = VoronoiEdge(face1, face3) edge3 = VoronoiEdge(face1, face4) # Verify that edge2 and edge3 intersect edge1 in the same place. p1 = edge1.get_line().intersection(edge2.get_line()) p2 = edge1.get_line().intersection(edge3.get_line()) np_tst.assert_array_almost_equal(p1, p2) # Verify that when tasked with distinguishing between the two, it # recognizes that edge3 is the correct choice choices = [edge2, edge3] self.assertTrue(edge1.is_ccw(edge2=edge2)) self.assertEqual(edge3, edge1.find_next_edge(choices)) # Add more conflicting choices. image = AtomImage(self.cell.get_atom(0), [-2, 0, 0]) face4 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # A farther edge. choices.append(VoronoiEdge(face1, face4)) image = AtomImage(self.cell.get_atom(0), [1, 0, 0]) face4 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # A CW edge. choices.append(VoronoiEdge(face1, face4)) self.assertEqual(edge3, edge1.find_next_edge(choices)) def test_pair(self): # Initialize faces. image = AtomImage(self.cell.get_atom(0), [0, 0, 1]) face1 = VoronoiFace(self.cell.get_atom(0), image, radical=True) image = AtomImage(self.cell.get_atom(0), [0, 1, 0]) face2 = VoronoiFace(self.cell.get_atom(0), image, radical=True) # Create edge. edge = VoronoiEdge(face1, face2) # Create pair. pair = edge.generate_pair() # Tests. self.assertEqual(edge.get_edge_face(), pair.get_intersecting_face()) self.assertEqual(edge.get_intersecting_face(), pair.get_edge_face()) dir1 = edge.get_line().get_direction() dir2 = -1 * pair.get_line().get_direction() np_tst.assert_array_almost_equal(dir1, dir2)
def test_FCC(self): # Create cell. structure = Cell() structure.add_atom(Atom([0, 0, 0], 0)) structure.add_atom(Atom([0.5, 0.5, 0], 0)) structure.add_atom(Atom([0.5, 0, 0.5], 0)) structure.add_atom(Atom([0, 0.5, 0.5], 0)) # Create cell for atom1. cell = VoronoiCell(structure.get_atom(0), radical=True) # Compute faces. images = [ AtomImage(structure.get_atom(i), sc) for i in range(4) for sc in VectorCombinationComputer( structure.get_lattice_vectors(), 4.0).get_supercell_coordinates() ] faces = cell.compute_faces(images) # Get direct neighbors. direct_faces = cell.compute_direct_neighbors(faces) self.assertTrue(direct_faces[0].get_face_distance() <= direct_faces[-1].get_face_distance()) # Simple tests. self.assertEqual(12, len(direct_faces)) self.assertEqual(len(images) - 12 - 1, len(faces)) # Make sure direct faces match up with expectations. neighboring_faces = [] neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(1), [0, 0, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(1), [0, -1, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(1), [-1, 0, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(1), [-1, -1, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(2), [-1, 0, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(2), [-1, 0, -1]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(2), [0, 0, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(2), [0, 0, -1]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(3), [0, 0, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(3), [0, 0, -1]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(3), [0, -1, 0]), radical=True)) neighboring_faces.append( VoronoiFace(structure.get_atom(0), AtomImage(structure.get_atom(3), [0, -1, -1]), radical=True)) # Test whether they are all there. for f in neighboring_faces: direct_faces.remove(f) self.assertTrue(len(direct_faces) == 0)
class testPairDistanceAnalysis(unittest.TestCase): def setUp(self): self.structure = Cell() self.structure.set_basis(lengths=[1, 1, 1], angles=[90, 90, 90]) self.structure.add_atom(Atom([0, 0, 0], 0)) self.pda = PairDistanceAnalysis() self.pda.analyze_structure(self.structure) def tearDown(self): self.structure = None self.pda = None def test_get_all_neighbors_of_atom(self): # With orthorhombic basis. self.pda.set_cutoff_distance(1.1) output = self.pda.get_all_neighbors_of_atom(0) self.assertEqual(6, len(output)) self.assertAlmostEqual(1.0, output[0][1], delta=1e-6) # Adding a second atom. self.structure.add_atom(Atom([0.5, 0.5, 0.5], 0)) output = self.pda.get_all_neighbors_of_atom(0) self.assertEqual(14, len(output)) # Altering the basis to something weird. new_basis = self.structure.get_basis() new_basis[1][0] = 14 output = self.pda.get_all_neighbors_of_atom(0) self.assertEqual(14, len(output)) # Check that images match up. center_pos = self.structure.get_atom(0).get_position_cartesian() for image in output: v = image[0].get_position() - center_pos self.assertAlmostEqual(image[1], norm(v), delta=1e-6) def test_PRDF(self): # With orthorhombic basis. self.pda.set_cutoff_distance(2.1) # Run code. prdf = self.pda.compute_PRDF(50) self.assertEqual(1, len(prdf)) self.assertEqual(1, len(prdf[0])) self.assertEqual(50, len(prdf[0][0])) # Make sure that it finds 4 peaks. n_peaks = 0 for val in prdf[0][0]: if val > 0: n_peaks += 1 self.assertEqual(4, n_peaks) # Add another atom, repeat. self.structure.add_atom(Atom([0.5, 0.5, 0.5], 1)) # Run again. prdf = self.pda.compute_PRDF(50) self.assertEqual(2, len(prdf)) self.assertEqual(2, len(prdf[0])) self.assertEqual(50, len(prdf[0][0])) # Make sure A-B prdf has 2 peaks. n_peaks = 0 for val in prdf[0][1]: if val > 0: n_peaks += 1 self.assertEqual(2, n_peaks) # Increase basis. self.structure.set_basis(lengths=[2, 2, 2], angles=[90, 90, 90]) self.pda.analyze_structure(self.structure) # Run again. prdf = self.pda.compute_PRDF(50) self.assertEqual(2, len(prdf)) self.assertEqual(2, len(prdf[0])) self.assertEqual(50, len(prdf[0][0])) # Make sure A-B prdf has 1 peaks. n_peaks = 0 for val in prdf[0][1]: if val > 0: n_peaks += 1 self.assertEqual(1, n_peaks)