Retrieving bounding box corners Point3d
-
I'm working on a placement tool and trying to determine which corner is which of the bounding box using the cursor... here's the code I came up with to try and do that...
Iterate selection...
@bbox_points_array=[] @coord=[] @selection.each{|entity| if entity.parent==@model parent=entity old_comp_origin=parent.transformation.origin trans=entity.transformation.to_a vector=Geom;;Vector3d.new(trans[0], trans[4], trans[8]) if trans[1]<0 multiplier=-1 else multiplier=1 end old_comp_angle=((X_AXIS.angle_between(vector)).radians)*multiplier @coord << old_comp_origin << old_comp_angle << parent parent_bounding_box=parent.bounds for i in 0..7 point=parent_bounding_box.corner(i) @bbox_points_array << point.to_a end end
... then use I use the cursor input point and compare it to the array I created above to see if there's a match... I round the decimals just to make them more legible...
cursor_input_point=@ip.position.to_a corner=0 @bb_corner=[] @main_module.bbox_point3d.each{|bbox_corner| bbox_input_point_array=[bbox_corner[0].round(6), bbox_corner[1].round(6), bbox_corner[2].round(6)] cursor_input_point_array=[cursor_input_point[0].round(6), cursor_input_point[1].round(6), cursor_input_point[2].round(6)] if bbox_input_point_array==cursor_input_point_array @bb_corner << corner end corner+=1 }
This works as long as the component is aligned with one of the axes if it's rotated ie: 45deg, the array point3ds are all off. I suspect this is due to the transformation that is applied to the component but I have no idea how to fix it.
Here's an example of an array with the compoent aligned on the x axis at origin [0, 0, 0]...
[[0.0, 0.0, 0.0], [22.000000000000007, 0.0, 0.0], [0.0, 22.000000000000007, 0.0], [22.000000000000007, 22.000000000000007, 0.0], [0.0, 0.0, 22.0], [22.000000000000007, 0.0, 22.0], [0.0, 22.000000000000007, 22.0], [22.000000000000007, 22.000000000000007, 22.0]]
and the same component rotated 45deg...
[[-15.55634918610406, -5.024295867788081e-15, 0.0], [15.556349186104041, -5.024295867788081e-15, 0.0], [-15.55634918610406, 31.112698372208097, 0.0], [15.556349186104041, 31.112698372208097, 0.0], [-15.55634918610406, -5.024295867788081e-15, 22.0], [15.556349186104041, -5.024295867788081e-15, 22.0], [-15.55634918610406, 31.112698372208097, 22.0], [15.556349186104041, 31.112698372208097, 22.0]]
Any ideas or suggestions?
-
using the transformation of the selected component, do an inverse transformation of the input point and compare that to the definition.bounds corners.
def onLButtonDown(flags, x, y, view) ph = view.pick_helper; ph.do_pick x,y; best=ph.best_picked if @status==0 && best.class==Sketchup;;ComponentInstance @comp = best @status=1; @status_text = "Pick a Corner" elsif @status==1 pt = @ip.position.transform @comp.transformation.inverse for i in 0..7 if pt==@comp.definition.bounds.corner(i) puts "This is corner #{i}"; break end end end end
-
I wrote an extension a few years ago that will draw the bounding box as edges: https://bitbucket.org/thomthom/draw-boundingbox/src/f08e7f6efba7712b56a535e4dae4ade3f9bde7af/src/tt_draw_bb/core.rb?at=master
You can rip that code if you want.
-
Thanks sdmitch that did the trick!
Thanks also tt_su for the code I'll def take a look at it but I'm able to draw the box except that it won't follow the orientation of the component. Is there a way to rotate the bbox once created?
Here's the code I'm using to create the bbox... credit needs to be given to Fredo that's where I got the code snipet.
bounding_box_corners=@boundingbox_lines.collect{|i| @main_module.bbox_point3d[i]} view.draw_lines(bounding_box_corners)
@boundingbox_lines=[0, 1, 1, 3, 3, 2, 2, 0, 4, 5, 5, 7, 7, 6, 6, 4, 0, 4, 1, 5, 2, 6, 3, 7]
ie of @main_module.bbox_point3d...
@main_module.bbox_point3d [Point3d(0, 0, 0), Point3d(22, 0, 0), Point3d(0, 22, 0), Point3d(22, 22, 0), Point3d(0, 0, 22), Point3d(22, 0, 22), Point3d(0, 22, 22), Point3d(22, 22, 22)] -
@frankn said:
Thanks also tt_su for the code I'll def take a look at it but I'm able to draw the box except that it won't follow the orientation of the component. Is there a way to rotate the bbox once created?
The BoundingBox object you get when you query the instance will always be oriented to world space. To get the bounding box as drawn in the UI you need to get the bounds of the definition - fetch all the points from its corners and transform them using the current edit_transform and the selected instance transform. That extension I linked to does all that.
-
@thomthom said:
The BoundingBox object you get when you query the instance will always be oriented to world space. To get the bounding box as drawn in the UI you need to get the bounds of the definition - fetch all the points from its corners and transform them using the current edit_transform and the selected instance transform. That extension I linked to does all that.
Ah! Thanks for the explaination ThomThom! I didn't realise that's what happened with instances' bounding boxes...very confusing for a novice!
I did take the time to check out your extension and was able to understand what you're doing and apply that to my own code... thanks again sir!
Advertisement