Tight Bounding Boxes for Breps

Demonstrates how to generate tight bounding boxes for Brep objects.

partial class Examples
{
  public static Result TightBoundingBox(RhinoDoc doc)
  {
    ObjRef obj_ref;
    var rc = RhinoGet.GetOneObject(
      "Select surface to split", true, ObjectType.Surface, out obj_ref);
    if (rc != Result.Success)
      return rc;
    var surface = obj_ref.Surface();
    if (surface == null)
      return Result.Failure;

    obj_ref = null;
    rc = RhinoGet.GetOneObject(
      "Select cutting curve", true, ObjectType.Curve, out obj_ref);
    if (rc != Result.Success)
      return rc;
    var curve = obj_ref.Curve();
    if (curve == null)
      return Result.Failure;

    var brep_face = surface as BrepFace;
    if (brep_face == null)
      return Result.Failure;

    var split-brep = brep_face.Split(
      new List<Curve> {curve}, doc.ModelAbsoluteTolerance);
    if (split-brep == null)
    {
      RhinoApp.WriteLine("Unable to split surface.");
      return Result.Nothing;
    }

    var meshes = Mesh.CreateFromBrep(split-brep);

    foreach (var mesh in meshes)
    {
      var bbox = mesh.GetBoundingBox(true);
      switch (bbox.IsDegenerate(doc.ModelAbsoluteTolerance))
      {
        case 3:
        case 2:
          return Result.Failure;
        case 1:
          // rectangle
          // box with 8 corners flattened to rectangle with 4 corners
          var rectangle_corners = bbox.GetCorners().Distinct().ToList();
          // add 1st point as last to close the loop
          rectangle_corners.Add(rectangle_corners[0]);
          doc.Objects.AddPolyline(rectangle_corners);
          doc.Views.Redraw();
          break;
        case 0:
          // box
          var brep_box = new Box(bbox).ToBrep();
          doc.Objects.AddBrep(brep_box);
          doc.Views.Redraw();
          break;
      }
    }

    return Result.Success;
  }
}
Partial Friend Class Examples
  Public Shared Function TightBoundingBox(ByVal doc As RhinoDoc) As Result
	Dim obj_ref As ObjRef = Nothing
	Dim rc = RhinoGet.GetOneObject("Select surface to split", True, ObjectType.Surface, obj_ref)
	If rc IsNot Result.Success Then
	  Return rc
	End If
	Dim surface = obj_ref.Surface()
	If surface Is Nothing Then
	  Return Result.Failure
	End If

	obj_ref = Nothing
	rc = RhinoGet.GetOneObject("Select cutting curve", True, ObjectType.Curve, obj_ref)
	If rc IsNot Result.Success Then
	  Return rc
	End If
	Dim curve = obj_ref.Curve()
	If curve Is Nothing Then
	  Return Result.Failure
	End If

	Dim brep_face = TryCast(surface, BrepFace)
	If brep_face Is Nothing Then
	  Return Result.Failure
	End If

	Dim split-brep = brep_face.Split(New List(Of Curve) From {curve}, doc.ModelAbsoluteTolerance)
	If split-brep Is Nothing Then
	  RhinoApp.WriteLine("Unable to split surface.")
	  Return Result.Nothing
	End If

	Dim meshes = Mesh.CreateFromBrep(split-brep)

	For Each mesh In meshes
	  Dim bbox = mesh.GetBoundingBox(True)
	  Select Case bbox.IsDegenerate(doc.ModelAbsoluteTolerance)
		Case 3, 2
		  Return Result.Failure
		Case 1
		  ' rectangle
		  ' box with 8 corners flattened to rectangle with 4 corners
		  Dim rectangle_corners = bbox.GetCorners().Distinct().ToList()
		  ' add 1st point as last to close the loop
		  rectangle_corners.Add(rectangle_corners(0))
		  doc.Objects.AddPolyline(rectangle_corners)
		  doc.Views.Redraw()
		Case 0
		  ' box
		  Dim brep_box = (New Box(bbox)).ToBrep()
		  doc.Objects.AddBrep(brep_box)
		  doc.Views.Redraw()
	  End Select
	Next mesh

	Return Result.Success
  End Function
End Class
from scriptcontext import doc
import rhinoscriptsyntax as rs
from Rhino.Geometry import *
from Rhino.Input import *
from Rhino.DocObjects import *
from Rhino.Commands import *
from System.Collections.Generic import *

def RunCommand():
    rc, obj_ref = RhinoGet.GetOneObject("Select surface to split", True, ObjectType.Surface)
    if rc != Result.Success:
        return rc
    brep_face = obj_ref.Surface()
    if brep_face == None:
        return Result.Failure

    rc, obj_ref = RhinoGet.GetOneObject("Select cutting curve", True, ObjectType.Curve)
    if rc != Result.Success:
        return rc
    curve = obj_ref.Curve()
    if curve == None:
        return Result.Failure

    curves = List[Curve]([curve])
    split-brep = brep_face.Split(curves, doc.ModelAbsoluteTolerance)

    if split-brep == None:
        RhinoApp.WriteLine("Unable to split surface.")
        return Result.Nothing

    meshes = Mesh.CreateFromBrep(split-brep)
    print type(meshes)
    for mesh in meshes:
        bbox = mesh.GetBoundingBox(True)
        bbox_type = bbox.IsDegenerate(doc.ModelAbsoluteTolerance)
        if bbox_type == 1: # rectangle
            # box with 8 corners flattened to rectangle with 4 corners
            box_corners = bbox.GetCorners()
            rectangle_corners = []
            for corner_point in box_corners:
                if corner_point not in rectangle_corners:
                    rectangle_corners.append(corner_point)
            # add 1st point as last to close the loop
            rectangle_corners.append(rectangle_corners[0])
            doc.Objects.AddPolyline(rectangle_corners)
            doc.Views.Redraw()
        elif bbox_type == 0: # box
            brep_box = Box(bbox).ToBrep()
            doc.Objects.AddBrep(brep_box)
            doc.Views.Redraw()
        else: # bbox invalid, point, or line
            return Result.Failure

    return Result.Success

if __name__ == "__main__":
    RunCommand()