Skip to content

Commit de2cef9

Browse files
committed
Expanded selector tests
1 parent a03648c commit de2cef9

File tree

1 file changed

+76
-34
lines changed

1 file changed

+76
-34
lines changed

tests/test_selectors.py

Lines changed: 76 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -103,32 +103,58 @@ def testFaceTypesFilter(self):
103103
def testPerpendicularDirFilter(self):
104104
c = CQ(makeUnitCube())
105105

106-
self.assertEqual(8, c.edges("#Z").size()) # 8 edges are perp. to z
107-
self.assertEqual(4, c.faces("#Z").size()) # 4 faces are perp to z too!
106+
perp_edges = c.edges("#Z")
107+
self.assertEqual(8, perp_edges.size()) # 8 edges are perp. to z
108+
# dot product of perpendicular vectors is zero
109+
for e in perp_edges.vals():
110+
self.assertAlmostEqual(e.tangentAt(0).dot(Vector(0, 0, 1)), 0.0)
111+
perp_faces = c.faces("#Z")
112+
self.assertEqual(4, perp_faces.size()) # 4 faces are perp to z too!
113+
for f in perp_faces.vals():
114+
self.assertAlmostEqual(f.normalAt(None).dot(Vector(0, 0, 1)), 0.0)
108115

109116
def testFaceDirFilter(self):
110117
c = CQ(makeUnitCube())
111118
# a cube has one face in each direction
112119
self.assertEqual(1, c.faces("+Z").size())
120+
self.assertTupleAlmostEquals(
121+
(0, 0, 1), c.faces("+Z").val().Center().toTuple(), 3
122+
)
113123
self.assertEqual(1, c.faces("-Z").size())
124+
self.assertTupleAlmostEquals(
125+
(0, 0, 0), c.faces("-Z").val().Center().toTuple(), 3
126+
)
114127
self.assertEqual(1, c.faces("+X").size())
115-
self.assertEqual(1, c.faces("X").size()) # should be same as +X
128+
self.assertTupleAlmostEquals(
129+
(0.5, 0, 0.5), c.faces("+X").val().Center().toTuple(), 3
130+
)
116131
self.assertEqual(1, c.faces("-X").size())
132+
self.assertTupleAlmostEquals(
133+
(-0.5, 0, 0.5), c.faces("-X").val().Center().toTuple(), 3
134+
)
117135
self.assertEqual(1, c.faces("+Y").size())
136+
self.assertTupleAlmostEquals(
137+
(0, 0.5, 0.5), c.faces("+Y").val().Center().toTuple(), 3
138+
)
118139
self.assertEqual(1, c.faces("-Y").size())
140+
self.assertTupleAlmostEquals(
141+
(0, -0.5, 0.5), c.faces("-Y").val().Center().toTuple(), 3
142+
)
119143
self.assertEqual(0, c.faces("XY").size())
144+
self.assertEqual(1, c.faces("X").size()) # should be same as +X
120145
self.assertEqual(c.faces("+X").val().Center(), c.faces("X").val().Center())
121146
self.assertNotEqual(c.faces("+X").val().Center(), c.faces("-X").val().Center())
122147

123148
def testParallelPlaneFaceFilter(self):
124149
c = CQ(makeUnitCube())
125150

126151
# faces parallel to Z axis
127-
self.assertEqual(2, c.faces("|Z").size())
128-
# TODO: provide short names for ParallelDirSelector
129-
self.assertEqual(
130-
2, c.faces(selectors.ParallelDirSelector(Vector((0, 0, 1)))).size()
131-
) # same thing as above
152+
# these two should produce the same behaviour:
153+
for s in ["|Z", selectors.ParallelDirSelector(Vector(0, 0, 1))]:
154+
parallel_faces = c.faces(s)
155+
self.assertEqual(2, parallel_faces.size())
156+
for f in parallel_faces.vals():
157+
self.assertAlmostEqual(abs(f.normalAt(None).dot(Vector(0, 0, 1))), 1)
132158
self.assertEqual(
133159
2, c.faces(selectors.ParallelDirSelector(Vector((0, 0, -1)))).size()
134160
) # same thing as above
@@ -138,9 +164,15 @@ def testParallelPlaneFaceFilter(self):
138164

139165
def testParallelEdgeFilter(self):
140166
c = CQ(makeUnitCube())
141-
self.assertEqual(4, c.edges("|Z").size())
142-
self.assertEqual(4, c.edges("|X").size())
143-
self.assertEqual(4, c.edges("|Y").size())
167+
for sel, vec in zip(
168+
["|X", "|Y", "|Z"], [Vector(1, 0, 0), Vector(0, 1, 0), Vector(0, 0, 1)]
169+
):
170+
edges = c.edges(sel)
171+
# each direction should have 4 edges
172+
self.assertEqual(4, edges.size())
173+
# each edge should be parallel with vec and have a cross product with a length of 0
174+
for e in edges.vals():
175+
self.assertAlmostEqual(e.tangentAt(0).cross(vec).Length, 0.0)
144176

145177
def testMaxDistance(self):
146178
c = CQ(makeUnitCube())
@@ -155,24 +187,28 @@ def testMaxDistance(self):
155187
self.assertAlmostEqual(1.0, v.Z, 3)
156188

157189
# test the case of multiple objects at the same distance
158-
el = c.edges("<Z").vals()
190+
el = c.edges(">Z").vals()
159191
self.assertEqual(4, len(el))
192+
for e in el:
193+
self.assertAlmostEqual(e.Center().z, 1)
160194

161195
def testMinDistance(self):
162196
c = CQ(makeUnitCube())
163197

164-
# should select the topmost face
198+
# should select the bottom face
165199
self.assertEqual(1, c.faces("<Z").size())
166200
self.assertEqual(4, c.faces("<Z").vertices().size())
167201

168-
# vertices should all be at z=1, if this is the top face
202+
# vertices should all be at z=0, if this is the bottom face
169203
self.assertEqual(4, len(c.faces("<Z").vertices().vals()))
170204
for v in c.faces("<Z").vertices().vals():
171205
self.assertAlmostEqual(0.0, v.Z, 3)
172206

173207
# test the case of multiple objects at the same distance
174208
el = c.edges("<Z").vals()
175209
self.assertEqual(4, len(el))
210+
for e in el:
211+
self.assertAlmostEqual(e.Center().z, 0)
176212

177213
def testNthDistance(self):
178214
c = Workplane("XY").pushPoints([(-2, 0), (2, 0)]).box(1, 1, 1)
@@ -252,20 +288,42 @@ def testNthDistance(self):
252288
val = c.faces("<Z[-2]").val()
253289
self.assertAlmostEqual(val.Center().z, 1)
254290

291+
# note that .val() will return the workplane center if the objects list
292+
# is empty, so to make sure this test fails with a selector that
293+
# selects nothing, use .vals()[0]
255294
# verify that <Z[-1] is equivalent to <Z
256-
val1 = c.faces("<Z[-1]").val()
257-
val2 = c.faces("<Z").val()
295+
val1 = c.faces("<Z[-1]").vals()[0]
296+
val2 = c.faces("<Z").vals()[0]
258297
self.assertTupleAlmostEquals(
259298
val1.Center().toTuple(), val2.Center().toTuple(), 3
260299
)
261300

262301
# verify that >Z[-1] is equivalent to >Z
263-
val1 = c.faces(">Z[-1]").val()
264-
val2 = c.faces(">Z").val()
302+
val1 = c.faces(">Z[-1]").vals()[0]
303+
val2 = c.faces(">Z").vals()[0]
265304
self.assertTupleAlmostEquals(
266305
val1.Center().toTuple(), val2.Center().toTuple(), 3
267306
)
268307

308+
# DirectionNthSelector should not select faces that are not perpendicular
309+
twisted_boxes = (
310+
Workplane()
311+
.box(1, 1, 1, centered=(True, True, False))
312+
.transformed(rotate=(45, 0, 0), offset=(0, 0, 3))
313+
.box(1, 1, 1)
314+
)
315+
self.assertTupleAlmostEquals(
316+
twisted_boxes.faces(">Z[-1]").val().Center().toTuple(), (0, 0, 1), 3
317+
)
318+
# this should select a face on the upper/rotated cube, not the lower/unrotated cube
319+
self.assertGreater(twisted_boxes.faces("<(0, 1, 1)[-1]").val().Center().z, 1)
320+
# verify that >Z[-1] is equivalent to >Z
321+
self.assertTupleAlmostEquals(
322+
twisted_boxes.faces(">(0, 1, 1)[0]").vals()[0].Center().toTuple(),
323+
twisted_boxes.faces("<(0, 1, 1)[-1]").vals()[0].Center().toTuple(),
324+
3,
325+
)
326+
269327
def testNearestTo(self):
270328
c = CQ(makeUnitCube(centered=False))
271329

@@ -453,22 +511,6 @@ def testRadiusNthSelector(self):
453511
wire_circles.wires(selectors.RadiusNthSelector(1)).val().radius(), 4
454512
)
455513

456-
# a polygon with rounded corners has a radius, according to OCCT
457-
loop_wire = Wire.makePolygon(
458-
[Vector(-10, 0, 0), Vector(0, 10, 0), Vector(10, 0, 0),]
459-
)
460-
loop_workplane = (
461-
Workplane().add(loop_wire.offset2D(1)).add(loop_wire.offset2D(2))
462-
)
463-
self.assertAlmostEqual(
464-
loop_workplane.wires(selectors.RadiusNthSelector(0)).val().radius(), 1.0
465-
)
466-
self.assertAlmostEqual(
467-
loop_workplane.wires(selectors.RadiusNthSelector(1)).val().radius(), 2.0
468-
)
469-
with self.assertRaises(IndexError):
470-
loop_workplane.wires(selectors.RadiusNthSelector(2))
471-
472514
def testAndSelector(self):
473515
c = CQ(makeUnitCube())
474516

0 commit comments

Comments
 (0)