diff --git a/assembly_mesh_plugin/plugin.py b/assembly_mesh_plugin/plugin.py index 02fabb0..22d9d5c 100644 --- a/assembly_mesh_plugin/plugin.py +++ b/assembly_mesh_plugin/plugin.py @@ -42,6 +42,34 @@ def get_tagged_gmsh(self): else: tagged_faces[short_name][tag] = [face.val()] + # Extract the tagged faces that have been added by the addSubshape method of cq.Assembly + if self._subshape_names: + for subshape, subshape_tag in self._subshape_names.items(): + if subshape_tag in tagged_faces[short_name]: + # Check to see if this is a duplicate + if subshape in tagged_faces[short_name][subshape_tag]: + print( + f"WARNING: Duplicate subshape found for tag {subshape_tag}." + ) + + tagged_faces[short_name][subshape_tag].append(subshape) + else: + tagged_faces[short_name][subshape_tag] = [subshape] + + # Extract the tagged faces that have been added by the addSubshape method of cq.Assembly + if self._subshape_layers: + for subshape, subshape_tag in self._subshape_layers.items(): + if subshape_tag in tagged_faces[short_name]: + # Check to see if this is a duplicate + if subshape in tagged_faces[short_name][subshape_tag]: + print( + f"WARNING: Duplicate subshape found for tag {subshape_tag}." + ) + + tagged_faces[short_name][subshape_tag].append(subshape) + else: + tagged_faces[short_name][subshape_tag] = [subshape] + # All the solids in the current part should be added to the mesh for s in obj.moved(loc).Solids(): # Add the current solid to the mesh diff --git a/pyproject.toml b/pyproject.toml index a474bd5..63626b4 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -6,7 +6,7 @@ build-backend = "hatchling.build" name = "assembly_mesh_plugin" version = "0.1.1" dependencies = [ - "cadquery", + "cadquery@git+https://github.com/CadQuery/cadquery.git", "gmsh", ] requires-python = ">=3.9" @@ -31,6 +31,9 @@ dev = [ "black", ] +[tool.hatch.metadata] +allow-direct-references = true + [project.urls] Repository = "https://github.com/cadquery/assembly-mesh-plugin.git" "Bug Tracker" = "https://github.com/cadquery/assembly-mesh-plugin/issues" diff --git a/tests/sample_assemblies.py b/tests/sample_assemblies.py index 7c69b61..ef01c81 100644 --- a/tests/sample_assemblies.py +++ b/tests/sample_assemblies.py @@ -262,3 +262,24 @@ def generate_assembly(): assembly.add(mat4_body, name="mat4", color=cq.Color("gray")) return assembly + + +def generate_subshape_assembly(): + """ + Generates a simple assembly with subshapes for testing. + """ + + # Create a simple assembly + assy = cq.Assembly(name="top-level") + cube_1 = cq.Workplane().box(10.0, 10.0, 10.0) + assy.add(cube_1, name="cube_1", color=cq.Color("green")) + + # Add subshape name, color and layer + assy.addSubshape( + cube_1.faces(">Z").val(), + name="cube_1_top_face", + color=cq.Color("red"), + layer="cube_1_top_face", + ) + + return assy diff --git a/tests/test_meshes.py b/tests/test_meshes.py index 928072b..c5e9f44 100644 --- a/tests/test_meshes.py +++ b/tests/test_meshes.py @@ -5,6 +5,7 @@ generate_simple_nested_boxes, generate_test_cross_section, generate_assembly, + generate_subshape_assembly, ) @@ -42,3 +43,39 @@ def test_simple_assembly(): continue assert cur_name in ["shell_inner-right", "insert_outer-right", "in_contact"] + + +def test_subshape_assembly(): + """ + Tests whether subshapes in assemblies get exported to physical groups in the resulting mesh. + """ + + # Generate a simple assembly with a subshape + assy = generate_subshape_assembly() + + # Create a mesh that has all the faces tagged as physical groups + assy.saveToGmsh(mesh_path="tagged_subshape_mesh.msh") + + gmsh.initialize() + + gmsh.open("tagged_subshape_mesh.msh") + + # Check the solids for the correct tags + physical_groups = gmsh.model.getPhysicalGroups(3) + for group in physical_groups: + # Get the name for the current volume + cur_name = gmsh.model.getPhysicalName(3, group[1]) + + assert cur_name in ["cube_1"] + + # Check the surfaces for the correct tags + physical_groups = gmsh.model.getPhysicalGroups(2) + for group in physical_groups: + # Get the name for this group + cur_name = gmsh.model.getPhysicalName(2, group[1]) + + # Skip any groups that are not tagged explicitly + if "_surface_" in cur_name: + continue + + assert cur_name in ["cube_1_cube_1_top_face"]