Newer
Older
beta-tester
committed
elif get_grease_pencil(object, context):
strokes = gstretch_get_strokes(object, context)
# straightening function (no GP) -> loops ignore modifiers
straightening = True
derived = False
bm_mod = bm.copy()
bm_mod.verts.ensure_lookup_table()
bm_mod.edges.ensure_lookup_table()
bm_mod.faces.ensure_lookup_table()
strokes = gstretch_get_fake_strokes(object, bm_mod, loops)
if not straightening:
derived, bm_mod = get_derived_bmesh(object, bm, context.scene)
beta-tester
committed
if get_grease_pencil(object, context):
derived, bm_mod, loops = get_connected_input(object, bm,
context.scene, input='selected')
mapping = get_mapping(derived, bm, bm_mod, False, False, loops)
loops = check_loops(loops, mapping, bm_mod)
# get strokes
beta-tester
committed
strokes = gstretch_get_strokes(object, context)
# straightening function (no GP) -> loops ignore modifiers
derived = False
mapping = False
bm_mod = bm.copy()
bm_mod.verts.ensure_lookup_table()
bm_mod.edges.ensure_lookup_table()
bm_mod.faces.ensure_lookup_table()
edge_keys = [
edgekey(edge) for edge in bm_mod.edges if
edge.select and not edge.hide
]
loops = get_connected_selections(edge_keys)
loops = check_loops(loops, mapping, bm_mod)
# create fake strokes
strokes = gstretch_get_fake_strokes(object, bm_mod, loops)
CoDEmanX
committed
# saving cache for faster execution next time
if not cached:
if strokes:
safe_strokes = gstretch_true_to_safe_strokes(strokes)
else:
safe_strokes = []
cache_write("Gstretch", object, bm, False, False,
safe_strokes, loops, derived, mapping)
# pair loops and strokes
ls_pairs = gstretch_match_loops_strokes(loops, strokes, object, bm_mod)
ls_pairs = gstretch_align_pairs(ls_pairs, object, bm_mod, self.method)
CoDEmanX
committed
if not loops:
# no selected geometry, convert GP to verts
if strokes:
move.append(gstretch_create_verts(object, bm, strokes,
self.method, self.conversion, self.conversion_distance,
self.conversion_max, self.conversion_min,
self.conversion_vertices))
for stroke in strokes:
gstretch_erase_stroke(stroke, context)
elif ls_pairs:
for (loop, stroke) in ls_pairs:
move.append(gstretch_calculate_verts(loop, stroke, object,
bm_mod, self.method))
if self.delete_strokes:
if type(stroke) != bpy.types.GPencilStroke:
# in case of cached fake stroke, get the real one
beta-tester
committed
if get_grease_pencil(object, context):
strokes = gstretch_get_strokes(object, context)
if loops and strokes:
ls_pairs = gstretch_match_loops_strokes(loops,
strokes, object, bm_mod)
ls_pairs = gstretch_align_pairs(ls_pairs,
object, bm_mod, self.method)
for (l, s) in ls_pairs:
if l == loop:
stroke = s
break
if self.lock_x or self.lock_y or self.lock_z:
lock = [self.lock_x, self.lock_y, self.lock_z]
else:
lock = False
bmesh.update_edit_mesh(object.data, tessface=True, destructive=True)
move_verts(object, bm, mapping, move, lock, self.influence)
CoDEmanX
committed
# cleaning up
CoDEmanX
committed
bl_idname = "mesh.looptools_relax"
bl_label = "Relax"
bl_description = "Relax the loop, so it is smoother"
bl_options = {'REGISTER', 'UNDO'}
CoDEmanX
committed
4107
4108
4109
4110
4111
4112
4113
4114
4115
4116
4117
4118
4119
4120
4121
4122
4123
4124
4125
4126
4127
4128
4129
4130
4131
4132
4133
4134
4135
4136
input = EnumProperty(
name="Input",
items=(("all", "Parallel (all)", "Also use non-selected "
"parallel loops as input"),
("selected", "Selection", "Only use selected vertices as input")),
description="Loops that are relaxed",
default='selected'
)
interpolation = EnumProperty(
name="Interpolation",
items=(("cubic", "Cubic", "Natural cubic spline, smooth results"),
("linear", "Linear", "Simple and fast linear algorithm")),
description="Algorithm used for interpolation",
default='cubic'
)
iterations = EnumProperty(
name="Iterations",
items=(("1", "1", "One"),
("3", "3", "Three"),
("5", "5", "Five"),
("10", "10", "Ten"),
("25", "25", "Twenty-five")),
description="Number of times the loop is relaxed",
default="1"
)
regular = BoolProperty(
name="Regular",
description="Distribute vertices at constant distances along the loop",
default=True
)
CoDEmanX
committed
@classmethod
def poll(cls, context):
ob = context.active_object
return(ob and ob.type == 'MESH' and context.mode == 'EDIT_MESH')
CoDEmanX
committed
def draw(self, context):
layout = self.layout
col = layout.column()
CoDEmanX
committed
col.prop(self, "interpolation")
col.prop(self, "input")
col.prop(self, "iterations")
col.prop(self, "regular")
CoDEmanX
committed
def invoke(self, context, event):
# load custom settings
settings_load(self)
return self.execute(context)
CoDEmanX
committed
def execute(self, context):
# initialise
global_undo, object, bm = initialise()
settings_write(self)
# check cache to see if we can save time
cached, single_loops, loops, derived, mapping = cache_read("Relax",
object, bm, self.input, False)
if cached:
derived, bm_mod = get_derived_bmesh(object, bm, context.scene)
else:
# find loops
derived, bm_mod, loops = get_connected_input(object, bm,
context.scene, self.input)
mapping = get_mapping(derived, bm, bm_mod, False, False, loops)
loops = check_loops(loops, mapping, bm_mod)
knots, points = relax_calculate_knots(loops)
CoDEmanX
committed
# saving cache for faster execution next time
if not cached:
cache_write("Relax", object, bm, self.input, False, False, loops,
derived, mapping)
CoDEmanX
committed
for iteration in range(int(self.iterations)):
# calculate splines and new positions
tknots, tpoints = relax_calculate_t(bm_mod, knots, points,
self.regular)
splines = []
for i in range(len(knots)):
splines.append(calculate_splines(self.interpolation, bm_mod,
tknots[i], knots[i]))
move = [relax_calculate_verts(bm_mod, self.interpolation,
tknots, knots, tpoints, points, splines)]
move_verts(object, bm, mapping, move, False, -1)
CoDEmanX
committed
# cleaning up
if derived:
bm_mod.free()
terminate(global_undo)
CoDEmanX
committed
return{'FINISHED'}
# space operator
bl_idname = "mesh.looptools_space"
bl_label = "Space"
bl_description = "Space the vertices in a regular distrubtion on the loop"
bl_options = {'REGISTER', 'UNDO'}
CoDEmanX
committed
influence = FloatProperty(
name="Influence",
description="Force of the tool",
default=100.0,
min=0.0,
max=100.0,
precision=1,
subtype='PERCENTAGE'
)
input = EnumProperty(
name="Input",
items=(("all", "Parallel (all)", "Also use non-selected "
"parallel loops as input"),
4219
4220
4221
4222
4223
4224
4225
4226
4227
4228
4229
4230
4231
4232
4233
4234
4235
4236
4237
4238
4239
4240
4241
4242
4243
4244
("selected", "Selection", "Only use selected vertices as input")),
description="Loops that are spaced",
default='selected'
)
interpolation = EnumProperty(
name="Interpolation",
items=(("cubic", "Cubic", "Natural cubic spline, smooth results"),
("linear", "Linear", "Vertices are projected on existing edges")),
description="Algorithm used for interpolation",
default='cubic'
)
lock_x = BoolProperty(
name="Lock X",
description="Lock editing of the x-coordinate",
default=False
)
lock_y = BoolProperty(
name="Lock Y",
description="Lock editing of the y-coordinate",
default=False
)
lock_z = BoolProperty(
name="Lock Z",
description="Lock editing of the z-coordinate",
default=False
)
CoDEmanX
committed
@classmethod
def poll(cls, context):
ob = context.active_object
return(ob and ob.type == 'MESH' and context.mode == 'EDIT_MESH')
CoDEmanX
committed
def draw(self, context):
layout = self.layout
col = layout.column()
CoDEmanX
committed
col.prop(self, "interpolation")
col.prop(self, "input")
col.separator()
CoDEmanX
committed
col_move = col.column(align=True)
row = col_move.row(align=True)
if self.lock_x:
row.prop(self, "lock_x", text="X", icon='LOCKED')
row.prop(self, "lock_x", text="X", icon='UNLOCKED')
row.prop(self, "lock_y", text="Y", icon='LOCKED')
row.prop(self, "lock_y", text="Y", icon='UNLOCKED')
row.prop(self, "lock_z", text="Z", icon='LOCKED')
row.prop(self, "lock_z", text="Z", icon='UNLOCKED')
CoDEmanX
committed
def invoke(self, context, event):
# load custom settings
settings_load(self)
return self.execute(context)
CoDEmanX
committed
def execute(self, context):
# initialise
global_undo, object, bm = initialise()
settings_write(self)
# check cache to see if we can save time
cached, single_loops, loops, derived, mapping = cache_read("Space",
object, bm, self.input, False)
if cached:
derived, bm_mod = get_derived_bmesh(object, bm, context.scene)
else:
# find loops
derived, bm_mod, loops = get_connected_input(object, bm,
context.scene, self.input)
mapping = get_mapping(derived, bm, bm_mod, False, False, loops)
loops = check_loops(loops, mapping, bm_mod)
CoDEmanX
committed
# saving cache for faster execution next time
if not cached:
cache_write("Space", object, bm, self.input, False, False, loops,
derived, mapping)
CoDEmanX
committed
move = []
for loop in loops:
# calculate splines and new positions
loop[0].append(loop[0][0])
tknots, tpoints = space_calculate_t(bm_mod, loop[0][:])
splines = calculate_splines(self.interpolation, bm_mod,
tknots, loop[0][:])
move.append(space_calculate_verts(bm_mod, self.interpolation,
tknots, tpoints, loop[0][:-1], splines))
# move vertices to new locations
if self.lock_x or self.lock_y or self.lock_z:
lock = [self.lock_x, self.lock_y, self.lock_z]
else:
lock = False
move_verts(object, bm, mapping, move, lock, self.influence)
CoDEmanX
committed
# cleaning up
if derived:
bm_mod.free()
terminate(global_undo)
CoDEmanX
committed
return{'FINISHED'}
# ########################################
# ##### GUI and registration #############
# ########################################
# menu containing all tools
class VIEW3D_MT_edit_mesh_looptools(Menu):
bl_label = "LoopTools"
CoDEmanX
committed
def draw(self, context):
layout = self.layout
CoDEmanX
committed
layout.operator("mesh.looptools_bridge", text="Bridge").loft = False
layout.operator("mesh.looptools_circle")
layout.operator("mesh.looptools_curve")
layout.operator("mesh.looptools_flatten")
layout.operator("mesh.looptools_bridge", text="Loft").loft = True
layout.operator("mesh.looptools_relax")
layout.operator("mesh.looptools_space")
# panel containing all tools
class VIEW3D_PT_tools_looptools(Panel):
bl_space_type = 'VIEW_3D'
bl_region_type = 'TOOLS'
bl_context = "mesh_edit"
bl_label = "LoopTools"
def draw(self, context):
layout = self.layout
col = layout.column(align=True)
lt = context.window_manager.looptools
CoDEmanX
committed
# bridge - first line
split = col.split(percentage=0.15, align=True)
if lt.display_bridge:
split.prop(lt, "display_bridge", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_bridge", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_bridge", text="Bridge").loft = False
# bridge - settings
if lt.display_bridge:
box = col.column(align=True).box().column()
CoDEmanX
committed
# top row
col_top = box.column(align=True)
row = col_top.row(align=True)
col_left = row.column(align=True)
col_right = row.column(align=True)
col_right.active = lt.bridge_segments != 1
col_left.prop(lt, "bridge_segments")
col_right.prop(lt, "bridge_min_width", text="")
# bottom row
bottom_left = col_left.row()
bottom_left.active = lt.bridge_segments != 1
bottom_left.prop(lt, "bridge_interpolation", text="")
bottom_right = col_right.row()
bottom_right.active = lt.bridge_interpolation == 'cubic'
bottom_right.prop(lt, "bridge_cubic_strength")
# boolean properties
col_top.prop(lt, "bridge_remove_faces")
CoDEmanX
committed
# override properties
col_top.separator()
row.prop(lt, "bridge_twist")
row.prop(lt, "bridge_reverse")
CoDEmanX
committed
# circle - first line
split = col.split(percentage=0.15, align=True)
if lt.display_circle:
split.prop(lt, "display_circle", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_circle", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_circle")
# circle - settings
if lt.display_circle:
box = col.column(align=True).box().column()
box.prop(lt, "circle_fit")
box.separator()
CoDEmanX
committed
box.prop(lt, "circle_flatten")
row = box.row(align=True)
row.prop(lt, "circle_custom_radius")
row_right = row.row(align=True)
row_right.active = lt.circle_custom_radius
row_right.prop(lt, "circle_radius", text="")
box.prop(lt, "circle_regular")
box.separator()
CoDEmanX
committed
col_move = box.column(align=True)
row = col_move.row(align=True)
if lt.circle_lock_x:
row.prop(lt, "circle_lock_x", text="X", icon='LOCKED')
row.prop(lt, "circle_lock_x", text="X", icon='UNLOCKED')
row.prop(lt, "circle_lock_y", text="Y", icon='LOCKED')
row.prop(lt, "circle_lock_y", text="Y", icon='UNLOCKED')
row.prop(lt, "circle_lock_z", text="Z", icon='LOCKED')
row.prop(lt, "circle_lock_z", text="Z", icon='UNLOCKED')
col_move.prop(lt, "circle_influence")
CoDEmanX
committed
# curve - first line
split = col.split(percentage=0.15, align=True)
if lt.display_curve:
split.prop(lt, "display_curve", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_curve", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_curve")
# curve - settings
if lt.display_curve:
box = col.column(align=True).box().column()
box.prop(lt, "curve_interpolation")
box.prop(lt, "curve_restriction")
box.prop(lt, "curve_boundaries")
box.prop(lt, "curve_regular")
box.separator()
CoDEmanX
committed
col_move = box.column(align=True)
row = col_move.row(align=True)
if lt.curve_lock_x:
row.prop(lt, "curve_lock_x", text="X", icon='LOCKED')
row.prop(lt, "curve_lock_x", text="X", icon='UNLOCKED')
row.prop(lt, "curve_lock_y", text="Y", icon='LOCKED')
row.prop(lt, "curve_lock_y", text="Y", icon='UNLOCKED')
row.prop(lt, "curve_lock_z", text="Z", icon='LOCKED')
row.prop(lt, "curve_lock_z", text="Z", icon='UNLOCKED')
col_move.prop(lt, "curve_influence")
CoDEmanX
committed
# flatten - first line
split = col.split(percentage=0.15, align=True)
if lt.display_flatten:
split.prop(lt, "display_flatten", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_flatten", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_flatten")
# flatten - settings
if lt.display_flatten:
box = col.column(align=True).box().column()
box.prop(lt, "flatten_plane")
# box.prop(lt, "flatten_restriction")
CoDEmanX
committed
col_move = box.column(align=True)
row = col_move.row(align=True)
if lt.flatten_lock_x:
row.prop(lt, "flatten_lock_x", text="X", icon='LOCKED')
row.prop(lt, "flatten_lock_x", text="X", icon='UNLOCKED')
row.prop(lt, "flatten_lock_y", text="Y", icon='LOCKED')
row.prop(lt, "flatten_lock_y", text="Y", icon='UNLOCKED')
row.prop(lt, "flatten_lock_z", text="Z", icon='LOCKED')
row.prop(lt, "flatten_lock_z", text="Z", icon='UNLOCKED')
col_move.prop(lt, "flatten_influence")
CoDEmanX
committed
split = col.split(percentage=0.15, align=True)
if lt.display_gstretch:
split.prop(lt, "display_gstretch", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_gstretch", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_gstretch")
# gstretch settings
if lt.display_gstretch:
box = col.column(align=True).box().column()
box.prop(lt, "gstretch_method")
col_conv = box.column(align=True)
col_conv.prop(lt, "gstretch_conversion", text="")
if lt.gstretch_conversion == 'distance':
col_conv.prop(lt, "gstretch_conversion_distance")
elif lt.gstretch_conversion == 'limit_vertices':
row = col_conv.row(align=True)
row.prop(lt, "gstretch_conversion_min", text="Min")
row.prop(lt, "gstretch_conversion_max", text="Max")
elif lt.gstretch_conversion == 'vertices':
col_conv.prop(lt, "gstretch_conversion_vertices")
box.separator()
CoDEmanX
committed
col_move = box.column(align=True)
row = col_move.row(align=True)
if lt.gstretch_lock_x:
row.prop(lt, "gstretch_lock_x", text="X", icon='LOCKED')
row.prop(lt, "gstretch_lock_x", text="X", icon='UNLOCKED')
row.prop(lt, "gstretch_lock_y", text="Y", icon='LOCKED')
row.prop(lt, "gstretch_lock_y", text="Y", icon='UNLOCKED')
row.prop(lt, "gstretch_lock_z", text="Z", icon='LOCKED')
row.prop(lt, "gstretch_lock_z", text="Z", icon='UNLOCKED')
col_move.prop(lt, "gstretch_influence")
box.operator("remove.gp", text="Delete GP Strokes")
CoDEmanX
committed
# loft - first line
split = col.split(percentage=0.15, align=True)
if lt.display_loft:
split.prop(lt, "display_loft", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_loft", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_bridge", text="Loft").loft = True
# loft - settings
if lt.display_loft:
box = col.column(align=True).box().column()
CoDEmanX
committed
# top row
col_top = box.column(align=True)
row = col_top.row(align=True)
col_left = row.column(align=True)
col_right = row.column(align=True)
col_right.active = lt.bridge_segments != 1
col_left.prop(lt, "bridge_segments")
col_right.prop(lt, "bridge_min_width", text="")
# bottom row
bottom_left = col_left.row()
bottom_left.active = lt.bridge_segments != 1
bottom_left.prop(lt, "bridge_interpolation", text="")
bottom_right = col_right.row()
bottom_right.active = lt.bridge_interpolation == 'cubic'
bottom_right.prop(lt, "bridge_cubic_strength")
# boolean properties
col_top.prop(lt, "bridge_remove_faces")
col_top.prop(lt, "bridge_loft_loop")
CoDEmanX
committed
# override properties
col_top.separator()
row.prop(lt, "bridge_twist")
row.prop(lt, "bridge_reverse")
CoDEmanX
committed
# relax - first line
split = col.split(percentage=0.15, align=True)
if lt.display_relax:
split.prop(lt, "display_relax", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_relax", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_relax")
# relax - settings
if lt.display_relax:
box = col.column(align=True).box().column()
box.prop(lt, "relax_interpolation")
box.prop(lt, "relax_input")
box.prop(lt, "relax_iterations")
box.prop(lt, "relax_regular")
CoDEmanX
committed
# space - first line
split = col.split(percentage=0.15, align=True)
if lt.display_space:
split.prop(lt, "display_space", text="", icon='DOWNARROW_HLT')
else:
split.prop(lt, "display_space", text="", icon='RIGHTARROW')
split.operator("mesh.looptools_space")
# space - settings
if lt.display_space:
box = col.column(align=True).box().column()
box.prop(lt, "space_interpolation")
box.prop(lt, "space_input")
box.separator()
CoDEmanX
committed
col_move = box.column(align=True)
row = col_move.row(align=True)
if lt.space_lock_x:
row.prop(lt, "space_lock_x", text="X", icon='LOCKED')
row.prop(lt, "space_lock_x", text="X", icon='UNLOCKED')
row.prop(lt, "space_lock_y", text="Y", icon='LOCKED')
row.prop(lt, "space_lock_y", text="Y", icon='UNLOCKED')
row.prop(lt, "space_lock_z", text="Z", icon='LOCKED')
row.prop(lt, "space_lock_z", text="Z", icon='UNLOCKED')
col_move.prop(lt, "space_influence")
# property group containing all properties for the gui in the panel
class LoopToolsProps(PropertyGroup):
"""
Fake module like class
bpy.context.window_manager.looptools
"""
# general display properties
4628
4629
4630
4631
4632
4633
4634
4635
4636
4637
4638
4639
4640
4641
4642
4643
4644
4645
4646
4647
4648
4649
4650
4651
4652
4653
4654
4655
4656
4657
4658
4659
4660
4661
4662
4663
4664
4665
4666
4667
display_bridge = BoolProperty(
name="Bridge settings",
description="Display settings of the Bridge tool",
default=False
)
display_circle = BoolProperty(
name="Circle settings",
description="Display settings of the Circle tool",
default=False
)
display_curve = BoolProperty(
name="Curve settings",
description="Display settings of the Curve tool",
default=False
)
display_flatten = BoolProperty(
name="Flatten settings",
description="Display settings of the Flatten tool",
default=False
)
display_gstretch = BoolProperty(
name="Gstretch settings",
description="Display settings of the Gstretch tool",
default=False
)
display_loft = BoolProperty(
name="Loft settings",
description="Display settings of the Loft tool",
default=False
)
display_relax = BoolProperty(
name="Relax settings",
description="Display settings of the Relax tool",
default=False
)
display_space = BoolProperty(
name="Space settings",
description="Display settings of the Space tool",
default=False
)
CoDEmanX
committed
# bridge properties
4670
4671
4672
4673
4674
4675
4676
4677
4678
4679
4680
4681
4682
4683
4684
4685
4686
4687
4688
4689
4690
4691
4692
4693
4694
4695
4696
4697
4698
4699
4700
4701
4702
4703
4704
4705
4706
4707
bridge_cubic_strength = FloatProperty(
name="Strength",
description="Higher strength results in more fluid curves",
default=1.0,
soft_min=-3.0,
soft_max=3.0
)
bridge_interpolation = EnumProperty(
name="Interpolation mode",
items=(('cubic', "Cubic", "Gives curved results"),
('linear', "Linear", "Basic, fast, straight interpolation")),
description="Interpolation mode: algorithm used when creating segments",
default='cubic'
)
bridge_loft = BoolProperty(
name="Loft",
description="Loft multiple loops, instead of considering them as "
"a multi-input for bridging",
default=False
)
bridge_loft_loop = BoolProperty(
name="Loop",
description="Connect the first and the last loop with each other",
default=False
)
bridge_min_width = IntProperty(
name="Minimum width",
description="Segments with an edge smaller than this are merged "
"(compared to base edge)",
default=0,
min=0,
max=100,
subtype='PERCENTAGE'
)
bridge_mode = EnumProperty(
name="Mode",
items=(('basic', "Basic", "Fast algorithm"),
('shortest', "Shortest edge", "Slower algorithm with "
"better vertex matching")),
4709
4710
4711
4712
4713
4714
4715
4716
4717
4718
4719
4720
4721
4722
4723
4724
4725
4726
4727
4728
4729
4730
4731
4732
4733
4734
description="Algorithm used for bridging",
default='shortest'
)
bridge_remove_faces = BoolProperty(
name="Remove faces",
description="Remove faces that are internal after bridging",
default=True
)
bridge_reverse = BoolProperty(
name="Reverse",
description="Manually override the direction in which the loops "
"are bridged. Only use if the tool gives the wrong result",
default=False
)
bridge_segments = IntProperty(
name="Segments",
description="Number of segments used to bridge the gap (0=automatic)",
default=1,
min=0,
soft_max=20
)
bridge_twist = IntProperty(
name="Twist",
description="Twist what vertices are connected to each other",
default=0
)
CoDEmanX
committed
# circle properties
4737
4738
4739
4740
4741
4742
4743
4744
4745
4746
4747
4748
4749
4750
4751
4752
4753
4754
4755
4756
4757
4758
4759
4760
4761
4762
4763
4764
4765
4766
4767
4768
4769
4770
4771
4772
4773
4774
4775
4776
4777
4778
4779
4780
4781
4782
4783
4784
4785
4786
4787
4788
4789
circle_custom_radius = BoolProperty(
name="Radius",
description="Force a custom radius",
default=False
)
circle_fit = EnumProperty(
name="Method",
items=(("best", "Best fit", "Non-linear least squares"),
("inside", "Fit inside", "Only move vertices towards the center")),
description="Method used for fitting a circle to the vertices",
default='best'
)
circle_flatten = BoolProperty(
name="Flatten",
description="Flatten the circle, instead of projecting it on the mesh",
default=True
)
circle_influence = FloatProperty(
name="Influence",
description="Force of the tool",
default=100.0,
min=0.0,
max=100.0,
precision=1,
subtype='PERCENTAGE'
)
circle_lock_x = BoolProperty(
name="Lock X",
description="Lock editing of the x-coordinate",
default=False
)
circle_lock_y = BoolProperty(
name="Lock Y",
description="Lock editing of the y-coordinate",
default=False
)
circle_lock_z = BoolProperty(
name="Lock Z",
description="Lock editing of the z-coordinate",
default=False
)
circle_radius = FloatProperty(
name="Radius",
description="Custom radius for circle",
default=1.0,
min=0.0,
soft_max=1000.0
)
circle_regular = BoolProperty(
name="Regular",
description="Distribute vertices at constant distances along the circle",
default=True
)
# curve properties
curve_boundaries = BoolProperty(
name="Boundaries",
description="Limit the tool to work within the boundaries of the "
"selected vertices",
default=False
)
curve_influence = FloatProperty(
name="Influence",
description="Force of the tool",
default=100.0,
min=0.0,
max=100.0,
precision=1,
subtype='PERCENTAGE'
)
curve_interpolation = EnumProperty(
name="Interpolation",
items=(("cubic", "Cubic", "Natural cubic spline, smooth results"),
("linear", "Linear", "Simple and fast linear algorithm")),
4810
4811
4812
4813
4814
4815
4816
4817
4818
4819
4820
4821
4822
4823
4824
4825
4826
4827
4828
4829
4830
4831
4832
4833
4834
4835
4836
4837
4838
4839
4840
description="Algorithm used for interpolation",
default='cubic'
)
curve_lock_x = BoolProperty(
name="Lock X",
description="Lock editing of the x-coordinate",
default=False
)
curve_lock_y = BoolProperty(
name="Lock Y",
description="Lock editing of the y-coordinate",
default=False
)
curve_lock_z = BoolProperty(
name="Lock Z",
description="Lock editing of the z-coordinate",
default=False
)
curve_regular = BoolProperty(
name="Regular",
description="Distribute vertices at constant distances along the curve",
default=True
)
curve_restriction = EnumProperty(
name="Restriction",
items=(("none", "None", "No restrictions on vertex movement"),
("extrude", "Extrude only", "Only allow extrusions (no indentations)"),
("indent", "Indent only", "Only allow indentation (no extrusions)")),
description="Restrictions on how the vertices can be moved",
default='none'
)
CoDEmanX
committed
# flatten properties
4843
4844
4845
4846
4847
4848
4849
4850
4851
4852
4853
4854
4855
4856
4857
4858
4859
4860
4861
4862
4863
4864
4865
4866
4867
4868
flatten_influence = FloatProperty(
name="Influence",
description="Force of the tool",
default=100.0,
min=0.0,
max=100.0,
precision=1,
subtype='PERCENTAGE'
)
flatten_lock_x = BoolProperty(
name="Lock X",
description="Lock editing of the x-coordinate",
default=False)
flatten_lock_y = BoolProperty(name="Lock Y",
description="Lock editing of the y-coordinate",
default=False
)
flatten_lock_z = BoolProperty(
name="Lock Z",
description="Lock editing of the z-coordinate",
default=False
)
flatten_plane = EnumProperty(
name="Plane",
items=(("best_fit", "Best fit", "Calculate a best fitting plane"),
("normal", "Normal", "Derive plane from averaging vertex "
("view", "View", "Flatten on a plane perpendicular to the "
"viewing angle")),
description="Plane on which vertices are flattened",
default='best_fit'
)
flatten_restriction = EnumProperty(
name="Restriction",
items=(("none", "None", "No restrictions on vertex movement"),
("bounding_box", "Bounding box", "Vertices are restricted to "
"movement inside the bounding box of the selection")),
description="Restrictions on how the vertices can be moved",
default='none'
)
CoDEmanX
committed
gstretch_conversion = EnumProperty(
name="Conversion",
items=(("distance", "Distance", "Set the distance between vertices "
"of the converted grease pencil stroke"),
("limit_vertices", "Limit vertices", "Set the minimum and maximum "
"number of vertices that converted GP strokes will have"),
("vertices", "Exact vertices", "Set the exact number of vertices "
"that converted grease pencil strokes will have. Short strokes "
"with few points may contain less vertices than this number."),
("none", "No simplification", "Convert each grease pencil point "
4896
4897
4898
4899
4900
4901
4902
4903
4904
4905
4906
4907
4908
4909
4910
4911
4912
4913
4914
4915
4916
4917
4918
4919
4920
4921
4922
4923
4924
4925
4926
4927
4928
4929
4930
4931
4932
4933
4934
4935
4936
4937
4938
4939
4940
4941
4942
4943
4944
4945
4946
4947
4948
4949
4950
4951
4952
4953
4954
4955
4956
4957
4958
4959
4960
4961
4962
4963
4964
4965
4966
4967
4968
4969
4970
4971
4972
4973
4974
4975
4976
4977
description="If grease pencil strokes are converted to geometry, "
"use this simplification method",
default='limit_vertices'
)
gstretch_conversion_distance = FloatProperty(
name="Distance",
description="Absolute distance between vertices along the converted "
"grease pencil stroke",
default=0.1,
min=0.000001,
soft_min=0.01,
soft_max=100
)
gstretch_conversion_max = IntProperty(
name="Max Vertices",
description="Maximum number of vertices grease pencil strokes will "
"have, when they are converted to geomtery",
default=32,
min=3,
soft_max=500,
update=gstretch_update_min
)
gstretch_conversion_min = IntProperty(
name="Min Vertices",
description="Minimum number of vertices grease pencil strokes will "
"have, when they are converted to geomtery",
default=8,
min=3,
soft_max=500,
update=gstretch_update_max
)
gstretch_conversion_vertices = IntProperty(
name="Vertices",
description="Number of vertices grease pencil strokes will "
"have, when they are converted to geometry. If strokes have less "
"points than required, the 'Spread evenly' method is used",
default=32,
min=3,
soft_max=500
)
gstretch_delete_strokes = BoolProperty(
name="Delete strokes",
description="Remove Grease Pencil strokes if they have been used "
"for Gstretch. WARNING: DOES NOT SUPPORT UNDO",
default=False
)
gstretch_influence = FloatProperty(
name="Influence",
description="Force of the tool",
default=100.0,
min=0.0,
max=100.0,
precision=1,
subtype='PERCENTAGE'
)
gstretch_lock_x = BoolProperty(
name="Lock X",
description="Lock editing of the x-coordinate",
default=False
)
gstretch_lock_y = BoolProperty(
name="Lock Y",
description="Lock editing of the y-coordinate",
default=False
)
gstretch_lock_z = BoolProperty(
name="Lock Z",
description="Lock editing of the z-coordinate",
default=False
)
gstretch_method = EnumProperty(
name="Method",
items=(("project", "Project", "Project vertices onto the stroke, "
"using vertex normals and connected edges"),
("irregular", "Spread", "Distribute vertices along the full "
"stroke, retaining relative distances between the vertices"),
("regular", "Spread evenly", "Distribute vertices at regular "
"distances along the full stroke")),
description="Method of distributing the vertices over the Grease "
"Pencil stroke",
default='regular'
)
CoDEmanX
committed
# relax properties
4980
4981
4982
4983
4984
4985
4986
4987
4988
4989
4990
4991
4992
4993
4994
4995
4996
4997
4998
4999
5000
relax_input = EnumProperty(name="Input",
items=(("all", "Parallel (all)", "Also use non-selected "
"parallel loops as input"),
("selected", "Selection", "Only use selected vertices as input")),
description="Loops that are relaxed",
default='selected'
)
relax_interpolation = EnumProperty(
name="Interpolation",
items=(("cubic", "Cubic", "Natural cubic spline, smooth results"),
("linear", "Linear", "Simple and fast linear algorithm")),
description="Algorithm used for interpolation",
default='cubic'
)
relax_iterations = EnumProperty(name="Iterations",
items=(("1", "1", "One"),
("3", "3", "Three"),
("5", "5", "Five"),
("10", "10", "Ten"),
("25", "25", "Twenty-five")),
description="Number of times the loop is relaxed",