(n)certainties

GSAPP- Fall 2010

(n)certainties header image 3

Code Bon Appetit Mr Perkins


Option Explicit
'Script written by

Call Main()
Sub Main()

'set up
Dim TrailDensity 'number of hand trails for each machine
Dim NumOfRandomPts 'number of points on each circle
Dim WeavingLength
Dim InputSection 'distance between two trail sections
Dim InputLength 'distance between two circles
Dim maxDistance 'the maximum distance for weaving
Dim minDistance 'the minimum distance for weaving

Dim trailRadius : trailRadius = 1
Dim handsRadius : handsRadius = 1
Dim Knot : Knot = 0.1

'choose machine trails
Dim arrCrv : arrCrv = Rhino.GetObjects("pick the machine trails", 4)
Dim arrStrPts : arrStrPts = Rhino.GetObjects("pick the wave generators", 1)
Dim arrPts : arrPts = arrStrPts
Dim e
For e=0 To Ubound(arrPts)
arrPts(e) = Rhino.PointCoordinates(arrStrPts(e))
Next
Dim WeavingMode : WeavingMode = 1
WeavingMode = Rhino.GetInteger("please choose weaving mode(1: Rule A 2: Rule B)", WeavingMode)

If WeavingMode = 1 Then
TrailDensity = 3
NumOfRandomPts = 5
WeavingLength = 10
InputSection = 2
InputLength = 1
maxDistance = 1.5
minDistance = 0.2
Else
WeavingMode = 2
TrailDensity = 2
NumOfRandomPts = 4
WeavingLength = 1
InputSection = 2
InputLength = 1
maxDistance = 5
End If

Dim n
For n = 0 To Ubound(arrCrv)

Dim arrTrail : arrTrail = Machine(arrCrv(n),InputSection,TrailDensity, trailRadius, 0)

Dim i
For i = 0 To Ubound(arrTrail)
Dim arrSegs
If WeavingMode = 1 Then
arrSegs = GenerateSegs(arrTrail(i), InputLength, NumOfRandomPts, handsRadius, arrPts)
Else
arrSegs = Machine(arrTrail(i), InputLength, NumOfRandomPts, handsRadius, 1)
End If

Dim Curves: Curves = Connection_Generator(arrSegs, WeavingMode)

Dim k
For k = 0 To Ubound(Curves(0))
Dim Curve1 : Curve1 = Curves(0)(k)
Dim Curve2 : Curve2 = Curves(1)(k)
Call CurveSplitter(Curve1, Curve2, maxDistance, minDistance, WeavingLength, Knot)

Next

Next

Next

End Sub

Function Machine(strCrv, InputSection, trailNum, Radius, CreationMode)

Dim secNum : secNum = Int(Rhino.CurveLength(strCrv)/InputSection)
If secNum < 3 Then
secNum = 3
End If

Dim arrPtsOnCrv : arrPtsOnCrv = Rhino.DivideCurve(strCrv, secNum-1)

Dim i, j
If trailNum > 4 Then 'maximum value is 3
trailNum = 4
End If

Dim n : n = 0
ReDim conPt(secNum-1,trailNum-1) 'control points of trails
For i = 0 To secNum-1

Dim dblParameter : dblParameter = Rhino.CurveClosestPoint(strCrv, arrPtsOnCrv(i))
Dim arrPlane : arrPlane = Rhino.CurvePerpFrame (strCrv, dblParameter)
Dim r : r = Radius 'radius of the circles
Dim circle : circle = Rhino.AddCircle(arrPlane,r)
Dim domain : domain = Rhino.CurveDomain (circle)

For j = 0 To trailNum-1

Dim pos
If trailNum < 3 Then
If n+j=5 Then
n = -4
End If
pos = domain(1)*(1/4)*(n+j)

Else
If n+j=trailNum Then
n = -(trailNum-1)
End If
pos = domain(1)*(1/trailNum)*(n+j)

End If
conPt(i,j) = Rhino.AddPoint(Rhino.EvaluateCurve (circle,pos))

Next
n = n + 1
Rhino.DeleteObject circle

Next

Dim k, m
ReDim Trail(trailNum-1)
For k = 0 To trailNum-1
ReDim pts(secNum-1)
For m = 0 To secNum-1
pts(m) = Rhino.PointCoordinates(conPt(m,k))
Rhino.DeleteObject conPt(m,k)

Next

If CreationMode = 0 Then
Dim handTrail : handTrail = "handTrail"
Call Rhino.AddLayer(handTrail,RGB(255,0,0))
Call Rhino.CurrentLayer(handTrail)

Else
Dim segCurves : segCurves = "segCurves"
Call Rhino.AddLayer(segCurves,RGB(0,0,0))
Call Rhino.CurrentLayer(segCurves)

End If

Trail(k) = Rhino.AddInterpCurve(pts)
Next

Machine = Trail

End Function

Function GenerateSegs(strCrv, InputLength, NumOfRandomPts, handsRadius, arrPts)

GenerateSegs = Null
Dim segCurves : segCurves = "segCurves"
Call Rhino.AddLayer(segCurves,RGB(0,0,0))
Call Rhino.CurrentLayer(segCurves)

If Not rhino.IsCurve(strCrv) Then Exit Function
Dim NumOfCircles : NumOfCircles = Int(Rhino.CurveLength(strCrv)/InputLength)
If NumOfCircles < 3 Then
NumOfCircles = 3
End If

Dim arrPtsOnCrv : arrPtsOnCrv = Rhino.DivideCurve(strCrv, NumOfCircles-1)
ReDim arrSegCrvs(-1)

Dim i,j,k
ReDim arrAllRandomPts(2,NumOfCircles-1)

For i = 0 To 2 ' three generations of points in each circle
For j = 0 To NumOfCircles-1

Dim dblParameter : dblParameter = Rhino.CurveClosestPoint(strCrv, arrPtsOnCrv(j))
Dim arrPlane : arrPlane = Rhino.CurvePerpFrame (strCrv, dblParameter)
Dim dbl : dbl = Rhino.Distance(arrPlane(0), arrPts(0))
Dim r1 : r1 = handsRadius+0.5*sin(dbl) 'radius of outside circle
ReDim arrRandomPtsOnjLevel(NumOfRandomPts-1)
For k = 0 To NumOfRandomPts-1

Dim cir : cir = Rhino.AddCircle(arrPlane,r1)
Dim domain : domain = Rhino.CurveDomain (cir)

arrRandomPtsOnjLevel(k) = Rhino.EvaluateCurve (cir,domain(1)*sin((j+1)*dbl)*sin((k+1)*dbl)*cos((i+1)*dbl))
'arrRandomPtsOnjLevel(k) = Rhino.EvaluateCurve (cir,domain(1)*sin((j+1)*1)*sin((k+1)*1)*cos((i+1)*1))

Rhino.DeleteObject cir

Next
arrAllRandomPts(i,j) = arrRandomPtsOnjLevel
'Call Rhino.Addpoints(arrAllRandomPts(i,j))
Next

Next

Dim index
Dim onListPts : onListPts = arrAllRandomPts
For i=0 To NumOfCircles-3

For j=0 To NumOfRandomPts-1

Dim arrPt0 : arrPt0 = onListPts(0,i)(j)
index = Rhino.PointArrayClosestPoint(onListPts(1,i+1),arrPt0)
Dim arrPt1 : arrPt1 = onListPts(1,i+1)(index)
index = Rhino.PointArrayClosestPoint(onListPts(2,i+2),arrPt1)
Dim arrPt2 : arrPt2 = onListPts(2,i+2)(index)

ReDim Preserve arrSegCrvs(Ubound(arrSegCrvs)+1)
arrSegCrvs(Ubound(arrSegCrvs)) = Rhino.AddInterpCurve(array(arrPt0,arrPt1,arrPt2))
onListPts(2,i+2)(index) = Array(0,-100000000000000000000000000,0) 'change the chosen point's coordinate, so it will not be chosen again

Next

Next

GenerateSegs = arrSegCrvs

End Function

Function Connection_Generator(arrCurves, WeavingMode)

ReDim Crv1(Ubound(arrCurves)), Crv2(Ubound(arrCurves))

If WeavingMode = 1 Then
Dim i
For i = 0 To Ubound(arrCurves)
Dim testPts : testPts = Rhino.CurveStartPoint(arrCurves(i))
ReDim targetPts(-1)
Dim j
For j=0 To Ubound(arrCurves)
If Not i = j Then
ReDim Preserve targetPts(Ubound(targetPts)+1)
targetPts(Ubound(targetPts)) = Rhino.CurveMidPoint(arrCurves(j))

End If
Next

Dim index : index = Rhino.PointArrayClosestPoint(targetPts, testPts)
Crv1(i) = arrCurves(i)
Crv2(i) = arrCurves(index)

Next

Else

Dim k
For k = 0 To Ubound(arrCurves)
Crv1(k) = arrCurves(k)
If k = Ubound(arrCurves) Then
Crv2(k) = arrCurves(0)
Else
Crv2(k) = arrCurves(k+1)
End If
Next
End If
Connection_Generator = Array(Crv1, Crv2)

End Function

Function CurveSplitter(Curve1, Curve2, maxDistance, minDistance, WeavingLength, Knot)

Dim nSegments : nSegments = Int(Rhino.CurveLength(Curve1)/WeavingLength)
If nSegments < 2 Then
nSegments = 2
End If

Dim aPoints1 : aPoints1 = Rhino.DivideCurve(Curve1, nSegments)
Dim aPoints2 : aPoints2 = Rhino.DivideCurve(Curve2, nSegments)

Dim i
ReDim segCrvs1(nSegments-1), segCrvs2(nSegments-1), midPtSeg1(nSegments-1), midPtSeg2(nSegments-1)
ReDim strPtSeg1(nSegments-1),strPtSeg2(nSegments-1), endPtSeg1(nSegments-1), endPtSeg2(nSegments-1)
For i = 0 To Ubound(aPoints1)-1
Dim t0 : t0 = Rhino.CurveClosestPoint(Curve1, aPoints1(i))
Dim t1 : t1 = Rhino.CurveClosestPoint(Curve1, aPoints1(i+1))
segCrvs1(i) = Rhino.TrimCurve(Curve1, Array(t0, t1), False)
midPtSeg1(i) = Rhino.CurveMidPoint(segCrvs1(i))
strPtSeg1(i) = Rhino.CurveStartPoint(segCrvs1(i))
endPtSeg1(i) = Rhino.CurveEndPoint(segCrvs1(i))

Dim t2 : t2 = Rhino.CurveClosestPoint(Curve2, aPoints2(i))
Dim t3 : t3 = Rhino.CurveClosestPoint(Curve2, aPoints2(i+1))
segCrvs2(i) = Rhino.TrimCurve(Curve2, Array(t2, t3), False)
midPtSeg2(i)= Rhino.CurveMidPoint(segCrvs2(i))
strPtSeg2(i) = Rhino.CurveStartPoint(segCrvs2(i))
endPtSeg2(i) = Rhino.CurveEndPoint(segCrvs2(i))

Next

Dim j
For j = 0 To Ubound(segCrvs1)
Dim d0 : d0 = Rhino.Distance(midPtSeg1(j),midPtSeg2(j))
Dim d1 : d1 = Rhino.Distance(strPtSeg1(j), strPtSeg2(j))
Dim d2 : d2 = Rhino.Distance(endPtSeg1(j), endPtSeg2(j))
Dim distance : distance = (d0+d1+d2)/2

If distance < maxDistance And distance > minDistance Then
Call Weaving_Machine(segCrvs1(j), segCrvs2(j), 4, Knot)

End If

Next

Rhino.DeleteObjects segCrvs1
Rhino.DeleteObjects segCrvs2

End Function

Function Weaving_Machine(Curve1, Curve2, Num, r)

Dim weaving : weaving = "weaving"
Call Rhino.AddLayer(weaving,RGB(0,0,255))
Call Rhino.CurrentLayer(weaving)

Dim arrPtsOnCrv1 : arrPtsOnCrv1 = Rhino.DivideCurve(Curve1, Num-1)
Dim arrPtsOnCrv2 : arrPtsOnCrv2 = Rhino.DivideCurve(Curve2, Num-1)
ReDim cir1(Num-1), cir2(Num-1),closePt1(Num-1),closePt2(Num-1)
Dim i
Dim NumPts : NumPts = 3 'number of points on each circle
ReDim PtsOnCircle1(Num-1),arrPts1(Num-1), PtsOnCircle2(Num-1),arrPts2(Num-1)
For i = 0 To Num-1

Dim dblParameter1 : dblParameter1 = Rhino.CurveClosestPoint(Curve1, arrPtsOnCrv1(i))
Dim arrPlane1 : arrPlane1 = Rhino.CurvePerpFrame (Curve1, dblParameter1)
cir1(i) = Rhino.AddCircle(arrPlane1,r)
Dim dblParameter2 : dblParameter2 = Rhino.CurveClosestPoint(Curve2, arrPtsOnCrv2(i))
Dim arrPlane2 : arrPlane2 = Rhino.CurvePerpFrame (Curve2, dblParameter2)
cir2(i) = Rhino.AddCircle(arrPlane2,r)

closePt1(i) = Rhino.CurveClosestPoint(cir1(i),arrPtsOnCrv2(i))
closePt2(i) = Rhino.CurveClosestPoint(cir2(i),arrPtsOnCrv1(i))
Dim domain1 : domain1 = Rhino.CurveDomain(cir1(i))
Dim domain2 : domain2 = Rhino.CurveDomain(cir2(i))

PtsOnCircle1(i) = Array(Rhino.AddPoint(Rhino.EvaluateCurve (cir1(i), closePt1(i)+0.25*domain1(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir1(i), closePt1(i)+0.5*domain1(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir1(i), closePt1(i)+0.75*domain1(1))))
arrPts1(i) = Array(Rhino.PointCoordinates(PtsOnCircle1(i)(0)), Rhino.PointCoordinates(PtsOnCircle1(i)(1)), Rhino.PointCoordinates(PtsOnCircle1(i)(2)))
PtsOnCircle2(i) = Array(Rhino.AddPoint(Rhino.EvaluateCurve (cir2(i), closePt2(i)+0.25*domain2(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir2(i), closePt2(i)+0.5*domain2(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir2(i), closePt2(i)+0.75*domain2(1))))
arrPts2(i) = Array(Rhino.PointCoordinates(PtsOnCircle2(i)(0)), Rhino.PointCoordinates(PtsOnCircle2(i)(1)), Rhino.PointCoordinates(PtsOnCircle2(i)(2)))

Rhino.DeleteObject cir1(i)
Rhino.DeleteObject cir2(i)
Rhino.DeleteObjects PtsOnCircle1(i)
Rhino.DeleteObjects PtsOnCircle2(i)
Next

ReDim crvPts(-1)
Dim k
For k = 0 To Num-2 Step 1

Dim m
For m = 0 To 2
ReDim Preserve crvPts(Ubound(crvPts)+1)
crvPts(Ubound(crvPts)) = arrPts2(k)(m)
Next

For m = 0 To 2
ReDim Preserve crvPts(Ubound(crvPts)+1)
crvPts(Ubound(crvPts)) = arrPts1(k+1)(m)
Next

Next

Rhino.AddCurve crvPts

End Function



Option Explicit
'Script written by

Call Main()
Sub Main()

'set up
Dim TrailDensity 'number of hand trails for each machine
Dim NumOfRandomPts 'number of points on each circle
Dim WeavingLength
Dim InputSection 'distance between two trail sections
Dim InputLength 'distance between two circles
Dim maxDistance 'the maximum distance for weaving
Dim minDistance 'the minimum distance for weaving

Dim trailRadius : trailRadius = 1
Dim handsRadius : handsRadius = 1
Dim Knot : Knot = 0.1

'choose machine trails
Dim arrCrv : arrCrv = Rhino.GetObjects("pick the machine trails", 4)

Dim WeavingMode : WeavingMode = 1
WeavingMode = Rhino.GetInteger("please choose weaving mode(1: Rule A 2: Rule B)", WeavingMode)

If WeavingMode = 1 Then
TrailDensity = 2
NumOfRandomPts = 4
WeavingLength = 10
InputSection = 2
InputLength = 1
maxDistance = 1
minDistance = 0.3
Else
WeavingMode = 2
TrailDensity = 2
NumOfRandomPts = 4
WeavingLength = 1
InputSection = 2
InputLength = 1
maxDistance = 5
End If

Dim n
For n = 0 To Ubound(arrCrv)

Dim arrTrail : arrTrail = Machine(arrCrv(n),InputSection,TrailDensity, trailRadius, 0)

Dim i
For i = 0 To Ubound(arrTrail)
Dim arrSegs
If WeavingMode = 1 Then
arrSegs = GenerateSegs(arrTrail(i), InputLength, NumOfRandomPts, handsRadius)
Else
arrSegs = Machine(arrTrail(i), InputLength, NumOfRandomPts, handsRadius, 1)
End If

Dim Curves: Curves = Connection_Generator(arrSegs, WeavingMode)

Dim k
For k = 0 To Ubound(Curves(0))
Dim Curve1 : Curve1 = Curves(0)(k)
Dim Curve2 : Curve2 = Curves(1)(k)
Call CurveSplitter(Curve1, Curve2, maxDistance, minDistance, WeavingLength, Knot)

Next

Next

Next

End Sub

Function Machine(strCrv, InputSection, trailNum, Radius, CreationMode)

Dim secNum : secNum = Int(Rhino.CurveLength(strCrv)/InputSection)
If secNum < 3 Then
secNum = 3
End If

Dim arrPtsOnCrv : arrPtsOnCrv = Rhino.DivideCurve(strCrv, secNum-1)

Dim i, j
If trailNum > 4 Then 'maximum value is 3
trailNum = 4
End If

Dim n : n = 0
ReDim conPt(secNum-1,trailNum-1) 'control points of trails
For i = 0 To secNum-1

Dim dblParameter : dblParameter = Rhino.CurveClosestPoint(strCrv, arrPtsOnCrv(i))
Dim arrPlane : arrPlane = Rhino.CurvePerpFrame (strCrv, dblParameter)
Dim r : r = Radius 'radius of the circles
Dim circle : circle = Rhino.AddCircle(arrPlane,r)
Dim domain : domain = Rhino.CurveDomain (circle)

For j = 0 To trailNum-1

Dim pos
If trailNum < 3 Then
If n+j=5 Then
n = -4
End If
pos = domain(1)*(1/4)*(n+j)

Else
If n+j=trailNum Then
n = -(trailNum-1)
End If
pos = domain(1)*(1/trailNum)*(n+j)

End If
conPt(i,j) = Rhino.AddPoint(Rhino.EvaluateCurve (circle,pos))

Next
n = n + 1
Rhino.DeleteObject circle

Next

Dim k, m
ReDim Trail(trailNum-1)
For k = 0 To trailNum-1
ReDim pts(secNum-1)
For m = 0 To secNum-1
pts(m) = Rhino.PointCoordinates(conPt(m,k))
Rhino.DeleteObject conPt(m,k)

Next

If CreationMode = 0 Then
Dim handTrail : handTrail = "handTrail"
Call Rhino.AddLayer(handTrail,RGB(255,0,0))
Call Rhino.CurrentLayer(handTrail)

Else
Dim segCurves : segCurves = "segCurves"
Call Rhino.AddLayer(segCurves,RGB(0,0,0))
Call Rhino.CurrentLayer(segCurves)

End If

Trail(k) = Rhino.AddInterpCurve(pts)
Next

Machine = Trail

End Function

Function GenerateSegs(strCrv, InputLength, NumOfRandomPts, handsRadius)

GenerateSegs = Null
Dim segCurves : segCurves = "segCurves"
Call Rhino.AddLayer(segCurves,RGB(0,0,0))
Call Rhino.CurrentLayer(segCurves)

If Not rhino.IsCurve(strCrv) Then Exit Function
Dim NumOfCircles : NumOfCircles = Int(Rhino.CurveLength(strCrv)/InputLength)
If NumOfCircles < 3 Then
NumOfCircles = 3
End If

Dim arrPtsOnCrv : arrPtsOnCrv = Rhino.DivideCurve(strCrv, NumOfCircles-1)
ReDim arrSegCrvs(-1)

Dim i,j,k
ReDim arrAllRandomPts(2,NumOfCircles-1)

Dim n : n = 0
For i = 0 To 2 ' three generations of points in each circle

For j = 0 To NumOfCircles-1

Dim dblParameter : dblParameter = Rhino.CurveClosestPoint(strCrv, arrPtsOnCrv(j))
Dim arrPlane : arrPlane = Rhino.CurvePerpFrame (strCrv, dblParameter)

Dim r1 : r1 = handsRadius 'radius of outside circle
ReDim arrRandomPtsOnjLevel(NumOfRandomPts-1)
For k = 0 To NumOfRandomPts-1

Dim cir : cir = Rhino.AddCircle(arrPlane,r1)
Dim domain : domain = Rhino.CurveDomain(cir)

Dim pos
If n+k=NumOfRandomPts Then
n = -(NumOfRandomPts-1)
End If
pos = domain(1)*(1/NumOfRandomPts)*(n+k)*sin(i+1)
arrRandomPtsOnjLevel(k) = Rhino.EvaluateCurve(cir,pos)
Rhino.DeleteObject cir
Next
n = n+1
arrAllRandomPts(i,j) = arrRandomPtsOnjLevel
'Call Rhino.Addpoints(arrAllRandomPts(i,j))
Next

Next

Dim index
Dim onListPts : onListPts = arrAllRandomPts
For i=0 To NumOfCircles-3

For j=0 To NumOfRandomPts-1

Dim arrPt0 : arrPt0 = onListPts(0,i)(j)
index = Rhino.PointArrayClosestPoint(onListPts(1,i+1),arrPt0)
Dim arrPt1 : arrPt1 = onListPts(1,i+1)(index)
index = Rhino.PointArrayClosestPoint(onListPts(2,i+2),arrPt1)
Dim arrPt2 : arrPt2 = onListPts(2,i+2)(index)

ReDim Preserve arrSegCrvs(Ubound(arrSegCrvs)+1)
arrSegCrvs(Ubound(arrSegCrvs)) = Rhino.AddInterpCurve(array(onListPts(0,i)(j),onListPts(1,i+1)(j),onListPts(2,i+2)(j)))
'onListPts(2,i+2)(index) = Array(0,-100000000000000000000000000,0) 'change the chosen point's coordinate, so it will not be chosen again

Next

Next

GenerateSegs = arrSegCrvs

End Function

Function Connection_Generator(arrCurves, WeavingMode)

ReDim Crv1(Ubound(arrCurves)), Crv2(Ubound(arrCurves))

If WeavingMode = 1 Then
Dim i
For i = 0 To Ubound(arrCurves)
Dim testPts : testPts = Rhino.CurveStartPoint(arrCurves(i))
ReDim targetPts(-1)
Dim j
For j=0 To Ubound(arrCurves)
If Not i = j Then
ReDim Preserve targetPts(Ubound(targetPts)+1)
targetPts(Ubound(targetPts)) = Rhino.CurveMidPoint(arrCurves(j))

End If
Next

Dim index : index = Rhino.PointArrayClosestPoint(targetPts, testPts)
Crv1(i) = arrCurves(i)
Crv2(i) = arrCurves(index)

Next

Else

Dim k
For k = 0 To Ubound(arrCurves)
Crv1(k) = arrCurves(k)
If k = Ubound(arrCurves) Then
Crv2(k) = arrCurves(0)
Else
Crv2(k) = arrCurves(k+1)
End If
Next
End If
Connection_Generator = Array(Crv1, Crv2)

End Function

Function CurveSplitter(Curve1, Curve2, maxDistance, minDistance, WeavingLength, Knot)

Dim nSegments : nSegments = Int(Rhino.CurveLength(Curve1)/WeavingLength)
If nSegments < 2 Then
nSegments = 2
End If

Dim aPoints1 : aPoints1 = Rhino.DivideCurve(Curve1, nSegments)
Dim aPoints2 : aPoints2 = Rhino.DivideCurve(Curve2, nSegments)

Dim i
ReDim segCrvs1(nSegments-1), segCrvs2(nSegments-1), midPtSeg1(nSegments-1), midPtSeg2(nSegments-1)
ReDim strPtSeg1(nSegments-1),strPtSeg2(nSegments-1), endPtSeg1(nSegments-1), endPtSeg2(nSegments-1)
For i = 0 To Ubound(aPoints1)-1
Dim t0 : t0 = Rhino.CurveClosestPoint(Curve1, aPoints1(i))
Dim t1 : t1 = Rhino.CurveClosestPoint(Curve1, aPoints1(i+1))
segCrvs1(i) = Rhino.TrimCurve(Curve1, Array(t0, t1), False)
midPtSeg1(i) = Rhino.CurveMidPoint(segCrvs1(i))
strPtSeg1(i) = Rhino.CurveStartPoint(segCrvs1(i))
endPtSeg1(i) = Rhino.CurveEndPoint(segCrvs1(i))

Dim t2 : t2 = Rhino.CurveClosestPoint(Curve2, aPoints2(i))
Dim t3 : t3 = Rhino.CurveClosestPoint(Curve2, aPoints2(i+1))
segCrvs2(i) = Rhino.TrimCurve(Curve2, Array(t2, t3), False)
midPtSeg2(i)= Rhino.CurveMidPoint(segCrvs2(i))
strPtSeg2(i) = Rhino.CurveStartPoint(segCrvs2(i))
endPtSeg2(i) = Rhino.CurveEndPoint(segCrvs2(i))

Next

Dim j
For j = 0 To Ubound(segCrvs1)
Dim d0 : d0 = Rhino.Distance(midPtSeg1(j),midPtSeg2(j))
Dim d1 : d1 = Rhino.Distance(strPtSeg1(j), strPtSeg2(j))
Dim d2 : d2 = Rhino.Distance(endPtSeg1(j), endPtSeg2(j))
Dim distance : distance = (d0+d1+d2)/2

If distance < maxDistance And distance > minDistance Then
Call Weaving_Machine(segCrvs1(j), segCrvs2(j), 4, Knot)

End If

Next

Rhino.DeleteObjects segCrvs1
Rhino.DeleteObjects segCrvs2

End Function

Function Weaving_Machine(Curve1, Curve2, Num, r)

Dim weaving : weaving = "weaving"
Call Rhino.AddLayer(weaving,RGB(0,0,255))
Call Rhino.CurrentLayer(weaving)

Dim arrPtsOnCrv1 : arrPtsOnCrv1 = Rhino.DivideCurve(Curve1, Num-1)
Dim arrPtsOnCrv2 : arrPtsOnCrv2 = Rhino.DivideCurve(Curve2, Num-1)
ReDim cir1(Num-1), cir2(Num-1),closePt1(Num-1),closePt2(Num-1)
Dim i
Dim NumPts : NumPts = 3 'number of points on each circle
ReDim PtsOnCircle1(Num-1),arrPts1(Num-1), PtsOnCircle2(Num-1),arrPts2(Num-1)
For i = 0 To Num-1

Dim dblParameter1 : dblParameter1 = Rhino.CurveClosestPoint(Curve1, arrPtsOnCrv1(i))
Dim arrPlane1 : arrPlane1 = Rhino.CurvePerpFrame (Curve1, dblParameter1)
cir1(i) = Rhino.AddCircle(arrPlane1,r)
Dim dblParameter2 : dblParameter2 = Rhino.CurveClosestPoint(Curve2, arrPtsOnCrv2(i))
Dim arrPlane2 : arrPlane2 = Rhino.CurvePerpFrame (Curve2, dblParameter2)
cir2(i) = Rhino.AddCircle(arrPlane2,r)

closePt1(i) = Rhino.CurveClosestPoint(cir1(i),arrPtsOnCrv2(i))
closePt2(i) = Rhino.CurveClosestPoint(cir2(i),arrPtsOnCrv1(i))
Dim domain1 : domain1 = Rhino.CurveDomain(cir1(i))
Dim domain2 : domain2 = Rhino.CurveDomain(cir2(i))

PtsOnCircle1(i) = Array(Rhino.AddPoint(Rhino.EvaluateCurve (cir1(i), closePt1(i)+0.25*domain1(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir1(i), closePt1(i)+0.5*domain1(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir1(i), closePt1(i)+0.75*domain1(1))))
arrPts1(i) = Array(Rhino.PointCoordinates(PtsOnCircle1(i)(0)), Rhino.PointCoordinates(PtsOnCircle1(i)(1)), Rhino.PointCoordinates(PtsOnCircle1(i)(2)))
PtsOnCircle2(i) = Array(Rhino.AddPoint(Rhino.EvaluateCurve (cir2(i), closePt2(i)+0.25*domain2(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir2(i), closePt2(i)+0.5*domain2(1))), Rhino.AddPoint(Rhino.EvaluateCurve (cir2(i), closePt2(i)+0.75*domain2(1))))
arrPts2(i) = Array(Rhino.PointCoordinates(PtsOnCircle2(i)(0)), Rhino.PointCoordinates(PtsOnCircle2(i)(1)), Rhino.PointCoordinates(PtsOnCircle2(i)(2)))

Rhino.DeleteObject cir1(i)
Rhino.DeleteObject cir2(i)
Rhino.DeleteObjects PtsOnCircle1(i)
Rhino.DeleteObjects PtsOnCircle2(i)
Next

ReDim crvPts(-1)
Dim k
For k = 0 To Num-2 Step 1

Dim m
For m = 0 To 2
ReDim Preserve crvPts(Ubound(crvPts)+1)
crvPts(Ubound(crvPts)) = arrPts2(k)(m)
Next

For m = 0 To 2
ReDim Preserve crvPts(Ubound(crvPts)+1)
crvPts(Ubound(crvPts)) = arrPts1(k+1)(m)
Next

Next

Rhino.AddCurve crvPts

End Function