How do I get element beneath the selected Hex element in a mesh using PyDPF?
Ayush Kumar
Member, Moderator, Employee Posts: 456
✭✭✭✭
in Structures
Comments
-
The methodology used is:
- Get the normal and centroid of the selected element.
- Generate a 3D line passing through the centroid and along the normal.
- Get centroids of all the neighboring elements.
- Filter out the centroid with the smallest distance to the 3D line.
- Fetch the corresponding element ID to the centroid in step 4.
Below is the Python code using PyDPF for the above steps:
import numpy as np from ansys.dpf import core as dpf rst_path = r"\Path\to\file.rst" ds = dpf.DataSources(rst_path) model = dpf.Model(rst_path) mesh = model.metadata.meshed_region # Replace EID of the selected element eid = 1959 ms_eid = dpf.Scoping() ms_eid.ids = [eid] # Get Nodal scoping ns = dpf.Scoping() ns.ids = mesh.elements.element_by_id(eid).node_ids # Get neighbouring elements es = dpf.operators.scoping.transpose( mesh_scoping=ns, meshed_region=mesh, inclusive=1, requested_location=dpf.locations.elemental ) es_scoping = es.outputs.mesh_scoping_as_scoping.get_data() # Get normal on the element of interest normals_op = dpf.operators.geo.normals(mesh=mesh, mesh_scoping=ms_eid) normals = normals_op.outputs.field.get_data().data print(normals) # Get element centroids ec = model.operator("centroids") ec_f = ec.outputs.fields_container.get_data()[0] point_start = ec_f.get_entity_data_by_id(eid) ec_res_field = dpf.operators.scoping.rescope( fields=ec_f, mesh_scoping=es_scoping).outputs.fields_as_field.get_data() ec_res = ec_res_field.data def distance_to_line(A, B, C): # Calculate the distance of point C from the line AB n = B - A v = C - A distance = np.linalg.norm(np.cross(n, v)) / np.linalg.norm(n) return distance def find_nearest_points_along_line(points, start, direction): # Convert the line to a vector line_vec = direction / np.linalg.norm(direction) # Calculate distances for each point distances = [] for point in points: d = distance_to_line(start, start + line_vec, point) distances.append(d) # Sort points by distance sorted_indices = np.argsort(distances) nearest_indices = sorted_indices[:3] return nearest_indices # Get indices of points nearest to the normal nearest_indices = find_nearest_points_along_line(ec_res, point_start, normals) # Element beneath second_closest_index = nearest_indices[1] eid_res = ec_res_field.scoping.ids[second_closest_index] print(f"Element closest to centroid of Element {eid} is {eid_res}")
0