forked from mcneel/rhino-developer-samples
-
Notifications
You must be signed in to change notification settings - Fork 0
/
SampleEtoRebuildCurve.py
165 lines (148 loc) · 5.94 KB
/
SampleEtoRebuildCurve.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
################################################################################
# SampleEtoRebuildCurve.py
# Copyright (c) 2017 Robert McNeel & Associates.
# See License.md in the root of this repository for details.
################################################################################
# Imports
import Rhino
import scriptcontext as sc
import Rhino.UI
import Eto.Drawing as drawing
import Eto.Forms as forms
################################################################################
# Class to hold rebuild arguments
################################################################################
class RebuildCurveArgs():
# Initializer
def __init__(self):
self.PointCount = 0
self.Degree = 0
self.PreserveTangents = False
self.DeleteInput = True
# Validator
def IsValid(self):
if self.PointCount < 2 or self.PointCount > 32767: return False
if self.Degree < 1 or self.Degree > 11: return False
return True
################################################################################
# Rebuild curve dialog class
################################################################################
class RebuildCurveDialog(forms.Dialog[bool]):
# Initializer
def __init__(self, args):
self.Args = args
# Initialize dialog box
self.Title = 'Rebuild'
self.Padding = drawing.Padding(5)
# Create layout
layout = forms.DynamicLayout()
layout.Padding = drawing.Padding(5)
layout.Spacing = drawing.Size(5, 5)
layout.AddRow(self.CreateSteppers())
layout.AddRow(None) # spacer
layout.AddRow(self.CreateCheckBoxes())
layout.AddRow(None) # spacer
layout.AddRow(self.CreateButtons())
# Set the dialog content
self.Content = layout
# Creates numeric stepper controls
def CreateSteppers(self):
# Create labels
label0 = forms.Label(Text = 'Point count:')
label1 = forms.Label(Text = 'Degree:')
label2 = forms.Label(Text = '({})'.format(self.Args.PointCount))
label3 = forms.Label(Text = '({})'.format(self.Args.Degree))
# Create numeric steppers
self.PointCount = forms.NumericStepper(
Value = self.Args.PointCount,
MinValue = 2,
MaxValue = 32767
)
self.Degree = forms.NumericStepper(
Value = self.Args.Degree,
MinValue = 1,
MaxValue = 11
)
# Create table layout
layout = forms.DynamicLayout()
layout.Spacing = drawing.Size(5, 5)
layout.AddRow(label0, label2, self.PointCount)
layout.AddRow(label1, label3, self.Degree)
return layout
# Creates checkbox controls
def CreateCheckBoxes(self):
# Create checkboxes
self.DeleteInput = forms.CheckBox(
Text = 'Delete input',
Checked = self.Args.DeleteInput,
ThreeState = False
)
self.PreserveTangents = forms.CheckBox(
Text = 'Preserve tangent end directions',
Checked = self.Args.PreserveTangents,
ThreeState = False
)
# Create table layout
layout = forms.DynamicLayout()
layout.Spacing = drawing.Size(5, 5)
layout.AddRow (self.DeleteInput)
layout.AddRow (self.PreserveTangents)
return layout
# OK button click handler
def OnOkButtonClick(self, sender, e):
# Harvest control values before closing
self.Args.PointCount = self.PointCount.Value
self.Args.Degree = self.Degree.Value
self.Args.PreserveTangents = self.PreserveTangents.Checked
self.Args.DeleteInput = self.DeleteInput.Checked
self.Close(True)
# Cancel button click handler
def OnCancelButtonClick(self, sender, e):
self.Close(False)
# Create button controls
def CreateButtons(self):
# Create the default button
self.DefaultButton = forms.Button(Text = 'OK')
self.DefaultButton.Click += self.OnOkButtonClick
# Create the abort button
self.AbortButton = forms.Button(Text = 'Cancel')
self.AbortButton.Click += self.OnCancelButtonClick
# Create button layout
button_layout = forms.DynamicLayout()
button_layout.Spacing = drawing.Size(5, 5)
button_layout.AddRow(None, self.DefaultButton, self.AbortButton, None)
return button_layout
################################################################################
# Function to test the rebuild curve dialog
################################################################################
def TestRebuildCurve():
res, objref = Rhino.Input.RhinoGet.GetOneObject(
"Select curve to rebuild",
True,
Rhino.DocObjects.ObjectType.Curve
)
if res != Rhino.Commands.Result.Success: return
curve = objref.Curve()
if curve is None: return
nurb = curve.ToNurbsCurve()
if curve is None: return
args = RebuildCurveArgs()
args.PointCount = nurb.Points.Count
args.Degree = nurb.Degree
dlg = RebuildCurveDialog(args)
rc = dlg.ShowModal(Rhino.UI.RhinoEtoApp.MainWindow)
if rc and args.IsValid():
nurb = curve.Rebuild(args.PointCount, args.Degree, args.PreserveTangents)
if nurb:
if args.DeleteInput:
sc.doc.Objects.Replace(objref, nurb)
else:
sc.doc.Objects.Add(nurb, objref.Object().Attributes)
sc.doc.Views.Redraw()
################################################################################
# Check to see if this file is being executed as the "main" python
# script instead of being used as a module by some other python script
# This allows us to use the module which ever way we want.
################################################################################
if __name__ == "__main__":
TestRebuildCurve()