Rib Maker

This Rib fabrication Rhino script allows the user to select a surface, input the row and column count, specify the rib dimensions, then sit back, have a coffee and let the computer do the work.

Rhino Script

Option Explicit
'Script written by <David Mans>
'Adapted from concepts provided Andrew Payne of Lift Architects
'http://www.liftarchitects.com/
'Script adapted by <Neoarchaic Studio>
'Script version Thursday, April 02, 2009 12:47:23 AM

Call Main()
Sub Main()
	Dim surface, arrValue
	surface = Rhino.GetObject("Select Surface", 8, True)
	If isNull(surface) Then Exit Sub
	Call reparameterize(surface)
	
	arrValue = Rhino.PropertyListBox(array("Columns", "Rows", "Rib Height", "Rib Width", "Tile Spacing", "textHeight"), array(10, 10, 1, 0.2, 1, 0.25))
	If isNull(arrValue) Then Exit Sub
	
	Call Rhino.EnableRedraw(False)
	Dim bBox: bBox = Rhino.BoundingBox(surface)
	Dim dist: dist = Rhino.Distance(bBox(0), bBox(4))
	
	Dim grid, ribs, draw
	grid = projectGrid(surface, CInt(arrValue(0)), CInt(arrValue(1)))
	ribs = makeRib(grid, CDbl(arrValue(2)), CDbl(arrValue(3)), dist)
	draw = makeDrawing(ribs(1), CDbl(arrValue(4)), CDbl(arrValue(5)))
	Call Rhino.DeleteObjects(grid(0))
	Call Rhino.DeleteObjects(grid(1))
	
	Call Rhino.EnableRedraw(True)
End Sub
Function projectGrid(surface, cols, rows)
	projectGrid = Null
	Dim i,j,k,r,s
	Dim bBox, order, edge(3)
	Dim tCrv,crv(1),pCrv(),arrCrv,dom(1), cStp(1)
	
	bBox = Rhino.BoundingBox(surface)
	order = array(4, 5, 7, 6, 4, 7, 5, 6)
	
	r = 0
	For i = 0 To 3 Step 1
		edge(i) = Rhino.AddLine(bBox(order(r)), bBox(order(r + 1)))
		r = r + 2
	Next
	order = array(cols, rows)
	r = 0
	For i = 0 To 1 Step 1
		s = 0
		dom(0) = Rhino.CurveDomain(edge(r))
		dom(1) = Rhino.CurveDomain(edge(r + 1))
		cStp(0) = (dom(0)(1) - dom(0)(0)) / order(i)
		cStp(1) = (dom(1)(1) - dom(1)(0)) / order(i)
		For j = 0 To order(i) - 1 Step 1
			tCrv = Rhino.AddLine(Rhino.EvaluateCurve(edge(r), dom(0)(0) + cStp(0) * 0.5 + cStp(0) * j), Rhino.EvaluateCurve(edge(r + 1), dom(1)(0) + cStp(1) * 0.5 + cStp(1) * j))
			arrCrv = Rhino.ProjectCurveToSurface(tCrv, surface, Rhino.VectorReverse(Rhino.WorldXYPlane()(3)))
			Call Rhino.DeleteObject(tCrv)
			For k = 0 To uBound(arrCrv) Step 1
				ReDim Preserve pCrv(s)
				pCrv(s) = arrCrv(k)
				s = s + 1
			Next
		Next
		crv(i) = pCrv
		r = r + 2
	Next
	Call Rhino.DeleteObjects(edge)
	projectGrid = crv
End Function
Function makeRib(curves, height, width, zHeight)
	makeRib = Null
	Dim i,j,k,r
	Dim intersect, tPt
	Dim arrObject()
	Dim blnBlock, xVal, yVal, zVal, tPts(7)
	
	xVal = array(-width * 0.5, -width * 0.5, width * 0.5, width * 0.5)
	yVal = array(-width * 0.5, width * 0.5, width * 0.5, -width * 0.5)
	zVal = array(0, height * 2 + zHeight)
	r = 0
	For i = 0 To 1 Step 1
		For j = 0 To 3 Step 1
			tPts(r) = array(xVal(j), yVal(j), zVal(i))
			r = r + 1
		Next
	Next
	blnBlock = Rhino.AddBox(tPts)
	
	r = 0
	For i = 0 To uBound(curves(0)) Step 1
		For j = 0 To uBound(curves(1)) Step 1
			intersect = Rhino.CurveCurveIntersection(curves(0)(i), curves(1)(j))
			If isNull(intersect) Then 
			Else
				ReDim Preserve arrObject(r)
				tPt = intersect(0, 1)
				arrObject(r) = Rhino.CopyObject(blnBlock, array(0, 0, 0), tPt)
				r = r + 1
			End If
		Next
	Next
	
	Dim tRib, rib(), tCurve()
	Dim ribSet(1), cutRibs(1),tLine(1),ribCurve(1)
	
	tLine(0) = Rhino.AddLine(array(0, 0, 0), array(width, 0, 0))
	tLine(1) = Rhino.AddLine(array(0, 0, 0), array(0, width, 0))
	
	For i = 0 To 1 Step 1
		ReDim rib(uBOund(curves(i)))
		For j = 0 To uBOund(curves(i)) Step 1
			Call Rhino.AddTextDot(i &amp; "-" &amp; j, Rhino.CurveEndPoint(curves(i)(j)))
			tRib = Rhino.ExtrudeCurveStraight(curves(i)(j), array(0, 0, 0), array(0, 0, height))
			Call Rhino.MoveObject(tRib, Rhino.CurveEndPoint(tLine(i)), Rhino.CurveMidPoint(tLine(i)))
			rib(j) = Rhino.ExtrudeSurface(tRib, tLine(i))
			Call Rhino.DeleteObject(tRib)
		Next
		ribSet(i) = rib
	Next
	
	For i = 0 To 1 Step 1
		ReDim tCurve(uBound(ribSet(i)))
		If i = 0 Then 
			Call Rhino.MoveObjects(arrObject, array(0, 0, 0), array(0, 0, height * 0.5))
		Else
			Call Rhino.MoveObjects(arrObject, array(0, 0, 0), array(0, 0, -height * 2 - zHeight))
		End If
		cutRibs(i) = Rhino.BooleanDifference(ribSet(i), arrObject, False)
		For j = 0 To ubound(cutRibs(i)) Step 1
			tCurve(j) = Rhino.ProjectCurveToSurface(curves(i)(j), cutRibs(i)(j), Rhino.VectorReverse(Rhino.WorldXYPlane()(3)))(0)
		Next
		ribCurve(i) = tCurve
		Call Rhino.DeleteObjects(ribSet(i))
	Next
	
	Call Rhino.DeleteObjects(arrObject)
	Call Rhino.DeleteObjects(tLine)
	Call Rhino.DeleteObject(blnBlock)
	makeRib = array(cutRibs, ribCurve)
End Function
Function makeDrawing(arrCrvs, spacing, tHeight)
	makeDrawing = Null
	Dim i,j
	Dim cPlane, wPlane, bBox, tObject(), objects()
	ReDim objects(uBOund(arrCrvs))
	
	Dim pPt, tPt
	Dim xPos, yPos, tPos, ySet()
	
	For i = 0 To uBound(arrCrvs) Step 1
		ReDim tObject(uBound(arrCrvs(i)))
		For j = 0 To uBound(arrCrvs(i)) Step 1
			cPlane = Rhino.CurvePlane(arrCrvs(i)(j))
			wPlane = Rhino.WorldXYPlane()
			tObject(j) = Rhino.OrientObject(arrCrvs(i)(j), array(cPlane(0), Rhino.PointAdd(cPlane(0), cPlane(1)), Rhino.PointAdd(cPlane(0), cPlane(2))), array(wPlane(0), wPlane(1), wPlane(2)))
			bBox = Rhino.BoundingBox(tObject(j))
			Call Rhino.MoveObject(tObject(j), bBox(0), array(0, 0, 0))
		Next
		objects(i) = tObject
	Next
	yPos = 0
	For i = 0 To uBound(arrCrvs) Step 1
		tPos = 0
		xPos = 0
		ReDim ySet(uBound(arrCrvs(i)))
		For j = 0 To uBound(arrCrvs(i)) Step 1
			bBox = Rhino.BoundingBox(objects(i)(j))
			pPt = array(xPos, yPos, 0)
			If j > 0 Then
				tPos = xPos
				xPos = tPos + Rhino.Distance(bBox(0), bBox(1)) + spacing
			Else
				xPos = bBox(1)(0) + spacing
			End If
			Call Rhino.MoveObject(objects(i)(j), bBox(0), pPt)
			Call Rhino.AddText(i &amp; "-" &amp; j, Rhino.CurveStartPoint(objects(i)(j)), tHeight)
			ySet(j) = bBox(2)(1)
		Next
		yPos = Rhino.Max(ySet) + spacing
	Next
End Function
Function reparameterize(strCurveID)
	If Rhino.IsCurve(strCurveID) = True Then
		Call rhino.SelectObject(strCurveID)
		Call rhino.Command("reparameterize 0 1")
		Call rhino.UnselectAllObjects()
	End If
	If Rhino.IsSurface(strCurveID) = True Then
		Call rhino.SelectObject(strCurveID)
		Call rhino.Command("reparameterize 0 1 0 1")
		Call rhino.UnselectAllObjects()
	End If
End Function