Coverage for pyrc \ tests \ test_cell.py: 99%

139 statements  

« prev     ^ index     » next       coverage.py v7.13.5, created at 2026-04-13 16:59 +0200

1# ------------------------------------------------------------------------------- 

2# Copyright (C) 2026 Joel Kimmich, Tim Jourdan 

3# ------------------------------------------------------------------------------ 

4# License 

5# This file is part of PyRC, distributed under GPL-3.0-or-later. 

6# ------------------------------------------------------------------------------ 

7 

8import unittest 

9import numpy as np 

10from pyrc.core.components.templates import Cell # Replace with actual import 

11 

12 

13class TestCellPlacement(unittest.TestCase): 

14 

15 def setUp(self): 

16 self.cell = Cell(position=np.array([0.0, 0.0, 0.0]), 

17 delta=(2, 2, 2)) 

18 

19 # for testing of create_grid class_method 

20 self.grid_size = (3, 4, 5) 

21 self.delta = (1.5, 2.0, 2.5) 

22 self.grid = Cell.create_grid(self.grid_size, self.delta) 

23 

24 def test_place_adjacent_x(self): 

25 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

26 delta=(2, 2, 2)) 

27 self.cell.place_adjacent(other, "x") 

28 np.testing.assert_array_equal(other.position, np.array([2.0, 0.0, 0.0])) 

29 

30 def test_place_adjacent_minus_x(self): 

31 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

32 delta=(2, 2, 2)) 

33 self.cell.place_adjacent(other, "-x") 

34 np.testing.assert_array_equal(other.position, np.array([-2.0, 0.0, 0.0])) 

35 

36 def test_place_adjacent_simple(self): 

37 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

38 delta=(2, 2, 2)) 

39 self.cell.place_adjacent(other, "xy") 

40 np.testing.assert_array_equal(other.position, np.array([2.0, 2.0, 0.0])) 

41 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

42 delta=(2, 2, 2)) 

43 self.cell.place_adjacent(other, "x-y") 

44 np.testing.assert_array_equal(other.position, np.array([2.0, -2.0, 0.0])) 

45 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

46 delta=(2, 2, 3)) 

47 self.cell.place_adjacent(other, "x-yz") 

48 np.testing.assert_array_equal(other.position, np.array([2.0, -2.0, 2.5])) 

49 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

50 delta=(2, 2, 3)) 

51 self.cell.place_adjacent(other, "x-y+z") 

52 np.testing.assert_array_equal(other.position, np.array([2.0, -2.0, 2.5])) 

53 

54 def test_place_adjacent_at_vertex(self): 

55 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

56 delta=(2, 2, 2)) 

57 self.cell.place_adjacent(other, "xyz") 

58 np.testing.assert_array_equal(other.position, np.array([2.0, 2.0, 2.0])) 

59 

60 def test_place_adjacent_stack(self): 

61 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

62 delta=(2, 2, 2)) 

63 self.cell.place_adjacent(other, "++x++y-z") 

64 np.testing.assert_array_equal(other.position, np.array([0, 0, -2.0])) 

65 self.cell.place_adjacent(other, "++x++yz") 

66 np.testing.assert_array_equal(other.position, np.array([0, 0, 2.0])) 

67 self.cell.place_adjacent(other, "++x++y-+z") 

68 np.testing.assert_array_equal(other.position, np.array([0, 0, -2.0])) 

69 

70 def test_place_adjacent_with_space(self): 

71 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

72 delta=(2, 2, 2)) 

73 self.cell.place_adjacent(other, "x -y") 

74 np.testing.assert_array_equal(other.position, np.array([2.0, -2.0, 0.0])) 

75 

76 def test_place_adjacent_same_face(self): 

77 """ 

78 This places the new cell within the other at the same position. 

79 """ 

80 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

81 delta=(2, 2, 2)) 

82 self.cell.place_adjacent(other, "++x") 

83 np.testing.assert_array_equal(other.position, np.array([0.0, 0.0, 0.0])) 

84 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

85 delta=(2, 2, 2)) 

86 self.cell.place_adjacent(other, "--x") 

87 np.testing.assert_array_equal(other.position, np.array([0.0, 0.0, 0.0])) 

88 

89 def test_place_adjacent_plus_minus_notation(self): 

90 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

91 delta=(2, 2, 2)) 

92 self.cell.place_adjacent(other, "+-y") 

93 np.testing.assert_array_equal(other.position, np.array([0.0, 2.0, 0.0])) 

94 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

95 delta=(2, 2, 2)) 

96 self.cell.place_adjacent(other, "-+y") 

97 np.testing.assert_array_equal(other.position, np.array([0.0, -2.0, 0.0])) 

98 

99 def test_place_adjacent_different_sizes(self): 

100 other = Cell(position=np.array([0.0, 0.0, 0.0]), 

101 delta=(4, 2, 2)) 

102 self.cell.place_adjacent(other, "x") 

103 np.testing.assert_array_equal(other.position, np.array([3.0, 0.0, 0.0])) 

104 

105 def test_place_adjacent_preserves_unaligned_coordinates(self): 

106 other = Cell(position=np.array([10.0, 20.0, 30.0]), 

107 delta=(2, 2, 2)) 

108 self.cell.place_adjacent(other, "x") 

109 np.testing.assert_array_equal(other.position, np.array([2.0, 20.0, 30.0])) 

110 

111 def test_create_adjacent(self): 

112 new_cell = self.cell.create_adjacent("y", delta=(3.0, 3.0, 3.0)) 

113 self.assertIsInstance(new_cell, Cell) 

114 np.testing.assert_array_equal(new_cell.position, np.array([0.0, 2.5, 0.0])) 

115 self.assertEqual(new_cell.delta_x, 3.0) 

116 

117 def test_create_adjacent_with_position(self): 

118 new_cell = self.cell.create_adjacent("z", position=np.array([5.0, 5.0, 5.0]), 

119 delta=(2.0, 2.0, 2.0)) 

120 np.testing.assert_array_equal(new_cell.position, np.array([5.0, 5.0, 2.0])) 

121 

122 def test_create_grid_aligned(self): 

123 cells = self.cell.create_grid_aligned("x", (2, 2, 2), (4.0, 4.0, 4.0)) 

124 cells = cells.flatten() 

125 self.assertEqual(len(cells), 8) 

126 self.assertIsInstance(cells[0], Cell) 

127 np.testing.assert_array_equal(cells[0].delta, np.array([2.0, 2.0, 2.0])) 

128 np.testing.assert_array_equal(cells[0].position, np.array([2.0, -1, -1])) 

129 np.testing.assert_array_equal(cells[1].position, np.array([2.0, -1, 1])) 

130 np.testing.assert_array_equal(cells[4].position, np.array([4.0, -1, -1])) 

131 

132 def test_create_grid_aligned_positioning(self): 

133 cells: np.ndarray = self.cell.create_grid_aligned("x", (2, 1, 1), (4.0, 2.0, 2.0)) 

134 cells = cells.flatten() 

135 self.assertEqual(len(cells), 2) 

136 np.testing.assert_array_almost_equal(cells[0].position, np.array([2.0, 0, 0.0])) 

137 np.testing.assert_array_almost_equal(cells[1].position, np.array([4.0, 0.0, 0.0])) 

138 

139 def test_inherited_class(self): 

140 class SpecialCell(Cell): 

141 def __init__(self, position, delta, special=None): 

142 super().__init__(position, delta) 

143 self.special = special 

144 

145 _special = SpecialCell(np.array([0.0, 0.0, 0.0]), (2.0, 2.0, 2.0), special=42) 

146 new_special = _special.create_adjacent("x", delta=(2.0, 2.0, 2.0), special=99) 

147 self.assertIsInstance(new_special, SpecialCell) 

148 self.assertEqual(new_special.special, 99) 

149 

150 def test_create_grid_return_type_and_shape(self): 

151 """Grid has correct type and shape.""" 

152 self.assertIsInstance(self.grid, np.ndarray) 

153 self.assertEqual(self.grid.shape, self.grid_size) 

154 

155 def test_create_grid_all_cells_are_cell_instances(self): 

156 """All elements are Cell instances.""" 

157 for cell in self.grid.flat: 

158 self.assertIsInstance(cell, Cell) 

159 

160 def test_create_grid_cell_deltas(self): 

161 """Each cell has correct delta dimensions.""" 

162 expected = np.array(self.delta) / np.array(self.grid_size) 

163 for cell in self.grid.flat: 

164 self.assertAlmostEqual(cell.delta_x, expected[0]) 

165 self.assertAlmostEqual(cell.delta_y, expected[1]) 

166 self.assertAlmostEqual(cell.delta_z, expected[2]) 

167 

168 def test_create_grid_center_position_default(self): 

169 """Grid center (mean of all positions) defaults to origin.""" 

170 positions = np.array([cell.position for cell in self.grid.flat]) 

171 np.testing.assert_allclose(positions.mean(axis=0), np.zeros(3), atol=1e-12) 

172 

173 def test_create_grid_center_position_custom(self): 

174 """Grid center (mean of all positions) equals specified center.""" 

175 center = np.array([1.0, 2.0, 3.0]) 

176 grid = Cell.create_grid(self.grid_size, self.delta, center_position=center) 

177 positions = np.array([cell.position for cell in grid.flat]) 

178 np.testing.assert_allclose(positions.mean(axis=0), center, atol=1e-12) 

179 

180 def test_create_grid_positions_spacing(self): 

181 """Adjacent cells are spaced by cell deltas.""" 

182 expected_deltas = np.array(self.delta) / np.array(self.grid_size) 

183 for ix in range(self.grid_size[0] - 1): 

184 diff = self.grid[ix + 1, 0, 0].position - self.grid[ix, 0, 0].position 

185 self.assertAlmostEqual(diff[0], expected_deltas[0]) 

186 for iy in range(self.grid_size[1] - 1): 

187 diff = self.grid[0, iy + 1, 0].position - self.grid[0, iy, 0].position 

188 self.assertAlmostEqual(diff[1], expected_deltas[1]) 

189 for iz in range(self.grid_size[2] - 1): 

190 diff = self.grid[0, 0, iz + 1].position - self.grid[0, 0, iz].position 

191 self.assertAlmostEqual(diff[2], expected_deltas[2]) 

192 

193 def test_create_grid_subclass_returns_subclass_instances(self): 

194 """Subclass call populates grid with subclass instances.""" 

195 

196 class SubCell(Cell): 

197 pass 

198 

199 grid = SubCell.create_grid(self.grid_size, self.delta) 

200 for cell in grid.flat: 

201 self.assertIsInstance(cell, SubCell) 

202 

203 

204if __name__ == "__main__": 

205 unittest.main()