I have been thinking for some time about the best way to know if two components intersect completely. It is necessary to take into account that some of them may not be solid.
I have thought of several ways but I do not see which is the right one because the results are not as expected.
- The first one was to make the intersection of the two boundingboxes but if the components are rotated I don’t get good points.
- The second option has been to project the corners of the boundingbox of one of the components on the plane of each of the faces of the second component and see if the projection of these points on the plane is also on the face. In this way it can happen that although the component is not in contact with the other component, the projection of the points on the plane of its faces if it is placed on one of the faces so it is not a good solution.
- The other option that has occurred to me is to project a raytest from the vertices of the faces towards the center of the boundingbox of the face and see if these raytests impact on the other component and calculate the percentage of the raytests that do impact.
100% = total intersection
0-100% = partial intersection
0% = no intersection
How do you see this solution? am I complicating too much?
# Check if exactly two items are selected
selection = Sketchup.active_model.selection
if selection.size == 2
object1 = nil
object2 = nil
# Identify objects 1 and 2
selection.each do |entity|
if entity.is_a?(Sketchup::Face)
object1 = entity
elsif entity.is_a?(Sketchup::ComponentInstance)
object2 = entity
end
end
# Verify that one object of each type has been found
if object1 && object2
# Initialize counters for raytest
hit_count = 0
total_rays = 0
# Calculate the center of the bounding box of the face
center = object1.bounds.center
# raytests from each vertex of object 1
object1.vertices.each do |vertex|
# vector from vertex to center of bounding box
vector = vertex.position.vector_to(center)
# ray from the vertex in the direction of the center of the bounding box
ray = [vertex.position, vector]
result = Sketchup.active_model.raytest(ray, false)
# Verify if the ray hits object 2
hit = result && result[1].include?(object2)
# Update counters
hit_count += 1 if hit
total_rays += 1
end
# raytests from the midpoint of each edge of the outer loop
outer_loop = object1.outer_loop
outer_loop.edges.each do |edge|
# center of the bounding box of the edge
mid_point = edge.bounds.center
# vector from the midpoint to the center of the bounding box
vector = mid_point.vector_to(center)
# ray from the midpoint in the direction of the center of the bounding box
ray = [mid_point, vector]
result = Sketchup.active_model.raytest(ray, false)
# Verify if the ray hits object 2
hit = result && result[1].include?(object2)
# Update counters
hit_count += 1 if hit
total_rays += 1
end
# Calculate and display the percentage of rays hitting object 2
percentage = (hit_count.to_f / total_rays) * 100
UI.messagebox("Percentage of rays hitting object 2: #{percentage.round(2)}%")
else
UI.messagebox("Please select one Face and one ComponentInstance.")
end
else
UI.messagebox("Please select only two elements.")
end