Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender-addons.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorStephen Leger <stephen@3dservices.ch>2018-11-16 17:31:26 +0300
committerStephen Leger <stephen@3dservices.ch>2018-11-16 17:34:51 +0300
commitbfbbd112c170d96e86838208b8781fd46df52514 (patch)
tree9fda29f608a32f8ac5a88e5873730bf6422dd280 /archipack
parent64198b8817042962dcdedc71bb81ee9492b19a4d (diff)
archipack 2.8 compatibility (step1)
Diffstat (limited to 'archipack')
-rw-r--r--archipack/__init__.py195
-rw-r--r--archipack/archipack_2d.py40
-rw-r--r--archipack/archipack_autoboolean.py102
-rw-r--r--archipack/archipack_cutter.py57
-rw-r--r--archipack/archipack_door.py272
-rw-r--r--archipack/archipack_fence.py218
-rw-r--r--archipack/archipack_floor.py181
-rw-r--r--archipack/archipack_gl.py740
-rw-r--r--archipack/archipack_handle.py6
-rw-r--r--archipack/archipack_keymaps.py6
-rw-r--r--archipack/archipack_manipulator.py345
-rw-r--r--archipack/archipack_material.py24
-rw-r--r--archipack/archipack_object.py41
-rw-r--r--archipack/archipack_preset.py30
-rw-r--r--archipack/archipack_reference_point.py42
-rw-r--r--archipack/archipack_rendering.py517
-rw-r--r--archipack/archipack_roof.py356
-rw-r--r--archipack/archipack_slab.py181
-rw-r--r--archipack/archipack_snap.py192
-rw-r--r--archipack/archipack_stair.py236
-rw-r--r--archipack/archipack_thumbs.py191
-rw-r--r--archipack/archipack_truss.py36
-rw-r--r--archipack/archipack_wall2.py377
-rw-r--r--archipack/archipack_window.py344
-rw-r--r--archipack/bmesh_utils.py10
25 files changed, 2324 insertions, 2415 deletions
diff --git a/archipack/__init__.py b/archipack/__init__.py
index 8b87585b..74f4f761 100644
--- a/archipack/__init__.py
+++ b/archipack/__init__.py
@@ -31,8 +31,8 @@ bl_info = {
'author': 's-leger',
'license': 'GPL',
'deps': '',
- 'version': (1, 2, 8),
- 'blender': (2, 7, 8),
+ 'version': (1, 2, 81),
+ 'blender': (2, 80, 0),
'location': 'View3D > Tools > Create > Archipack',
'warning': '',
'wiki_url': 'https://github.com/s-leger/archipack/wiki',
@@ -46,7 +46,6 @@ import os
if "bpy" in locals():
import importlib as imp
- imp.reload(archipack_progressbar)
imp.reload(archipack_material)
imp.reload(archipack_snap)
imp.reload(archipack_manipulator)
@@ -65,7 +64,6 @@ if "bpy" in locals():
# print("archipack: reload ready")
else:
- from . import archipack_progressbar
from . import archipack_material
from . import archipack_snap
from . import archipack_manipulator
@@ -81,8 +79,7 @@ else:
from . import archipack_truss
from . import archipack_floor
from . import archipack_rendering
-
- # print("archipack: ready")
+ print("archipack: ready")
# noinspection PyUnresolvedReferences
import bpy
@@ -105,82 +102,110 @@ icons_collection = {}
# Addon preferences
# ----------------------------------------------------
-def update_panel(self, context):
- try:
- bpy.utils.unregister_class(TOOLS_PT_Archipack_Tools)
- bpy.utils.unregister_class(TOOLS_PT_Archipack_Create)
- except:
- pass
- prefs = context.user_preferences.addons[__name__].preferences
- TOOLS_PT_Archipack_Tools.bl_category = prefs.tools_category
- bpy.utils.register_class(TOOLS_PT_Archipack_Tools)
- TOOLS_PT_Archipack_Create.bl_category = prefs.create_category
- bpy.utils.register_class(TOOLS_PT_Archipack_Create)
-
class Archipack_Pref(AddonPreferences):
bl_idname = __name__
- tools_category = StringProperty(
- name="Tools",
- description="Choose a name for the category of the Tools panel",
- default="Tools",
- update=update_panel
- )
- create_category = StringProperty(
- name="Create",
- description="Choose a name for the category of the Create panel",
- default="Create",
- update=update_panel
- )
- create_submenu = BoolProperty(
+ create_submenu : BoolProperty(
name="Use Sub-menu",
description="Put Achipack's object into a sub menu (shift+a)",
default=True
)
- max_style_draw_tool = BoolProperty(
+ max_style_draw_tool : BoolProperty(
name="Draw a wall use 3dsmax style",
description="Reverse clic / release & drag cycle for Draw a wall",
default=True
)
# Arrow sizes (world units)
- arrow_size = FloatProperty(
+ arrow_size : FloatProperty(
name="Arrow",
description="Manipulators arrow size (blender units)",
default=0.05
)
# Handle area size (pixels)
- handle_size = IntProperty(
+ handle_size : IntProperty(
name="Handle",
description="Manipulators handle sensitive area size (pixels)",
min=2,
default=10
)
- matlib_path = StringProperty(
+ constant_handle_size: BoolProperty(
+ name="Constant handle size",
+ description="When checked, handle size on scree remains constant (handle size pixels)",
+ default=False
+ )
+ text_size: IntProperty(
+ name="Manipulators",
+ description="Manipulator font size (pixels)",
+ min=2,
+ default=14
+ )
+ handle_colour_selected: FloatVectorProperty(
+ name="Selected handle colour",
+ description="Handle color when selected",
+ subtype='COLOR_GAMMA',
+ default=(0.0, 0.0, 0.7, 1.0),
+ size=4,
+ min=0, max=1
+ )
+ handle_colour_inactive: FloatVectorProperty(
+ name="Inactive handle colour",
+ description="Handle color when disabled",
+ subtype='COLOR_GAMMA',
+ default=(0.3, 0.3, 0.3, 1.0),
+ size=4,
+ min=0, max=1
+ )
+ handle_colour_normal: FloatVectorProperty(
+ name="Handle colour normal",
+ description="Base handle color when not selected",
+ subtype='COLOR_GAMMA',
+ default=(1.0, 1.0, 1.0, 1.0),
+ size=4,
+ min=0, max=1
+ )
+ handle_colour_hover: FloatVectorProperty(
+ name="Handle colour hover",
+ description="Handle color when mouse hover",
+ subtype='COLOR_GAMMA',
+ default=(1.0, 1.0, 0.0, 1.0),
+ size=4,
+ min=0, max=1
+ )
+ handle_colour_active: FloatVectorProperty(
+ name="Handle colour active",
+ description="Handle colour when moving",
+ subtype='COLOR_GAMMA',
+ default=(1.0, 0.0, 0.0, 1.0),
+ size=4,
+ min=0, max=1
+ )
+ matlib_path : StringProperty(
name="Folder path",
description="absolute path to material library folder",
- default=""
+ default="",
+ subtype="DIR_PATH"
)
# Font sizes and basic colour scheme
- feedback_size_main = IntProperty(
+ feedback_size_main : IntProperty(
name="Main",
description="Main title font size (pixels)",
min=2,
default=16
)
- feedback_size_title = IntProperty(
+ feedback_size_title : IntProperty(
name="Title",
description="Tool name font size (pixels)",
min=2,
default=14
)
- feedback_size_shortcut = IntProperty(
+ feedback_size_shortcut : IntProperty(
name="Shortcut",
description="Shortcuts font size (pixels)",
min=2,
default=11
)
- feedback_shortcut_area = FloatVectorProperty(
+ feedback_shortcut_area : FloatVectorProperty(
name="Background Shortcut",
description="Shortcut area background color",
subtype='COLOR_GAMMA',
@@ -188,7 +213,7 @@ class Archipack_Pref(AddonPreferences):
size=4,
min=0, max=1
)
- feedback_title_area = FloatVectorProperty(
+ feedback_title_area : FloatVectorProperty(
name="Background Main",
description="Title area background color",
subtype='COLOR_GAMMA',
@@ -196,7 +221,7 @@ class Archipack_Pref(AddonPreferences):
size=4,
min=0, max=1
)
- feedback_colour_main = FloatVectorProperty(
+ feedback_colour_main : FloatVectorProperty(
name="Font Main",
description="Title color",
subtype='COLOR_GAMMA',
@@ -204,7 +229,7 @@ class Archipack_Pref(AddonPreferences):
size=4,
min=0, max=1
)
- feedback_colour_key = FloatVectorProperty(
+ feedback_colour_key : FloatVectorProperty(
name="Font Shortcut key",
description="KEY label color",
subtype='COLOR_GAMMA',
@@ -212,7 +237,7 @@ class Archipack_Pref(AddonPreferences):
size=4,
min=0, max=1
)
- feedback_colour_shortcut = FloatVectorProperty(
+ feedback_colour_shortcut : FloatVectorProperty(
name="Font Shortcut hint",
description="Shortcuts text color",
subtype='COLOR_GAMMA',
@@ -226,21 +251,22 @@ class Archipack_Pref(AddonPreferences):
box = layout.box()
row = box.row()
col = row.column()
- col.label(text="Tab Category:")
- col.prop(self, "tools_category")
- col.prop(self, "create_category")
- col.prop(self, "create_submenu")
- box = layout.box()
- box.label("Features")
- box.prop(self, "max_style_draw_tool")
+ col.label(text="Setup actions")
+ col.prop(self, "matlib_path", text="Material library")
+ box.label(text="Render presets Thumbnails")
+ box.operator("archipack.render_thumbs", icon='ERROR')
box = layout.box()
row = box.row()
col = row.column()
- col.label(text="Material library:")
- col.prop(self, "matlib_path")
+ col.label(text="Add menu:")
+ col.prop(self, "create_submenu")
+
+ box = layout.box()
+ box.label(text="Features")
+ box.prop(self, "max_style_draw_tool")
box = layout.box()
row = box.row()
- split = row.split(percentage=0.5)
+ split = row.split(factor=0.5)
col = split.column()
col.label(text="Colors:")
row = col.row(align=True)
@@ -253,6 +279,16 @@ class Archipack_Pref(AddonPreferences):
row.prop(self, "feedback_colour_key")
row = col.row(align=True)
row.prop(self, "feedback_colour_shortcut")
+ row = col.row(align=True)
+ row.prop(self, "handle_colour_normal")
+ row = col.row(align=True)
+ row.prop(self, "handle_colour_hover")
+ row = col.row(align=True)
+ row.prop(self, "handle_colour_active")
+ row = col.row(align=True)
+ row.prop(self, "handle_colour_selected")
+ row = col.row(align=True)
+ row.prop(self, "handle_colour_inactive")
col = split.column()
col.label(text="Font size:")
col.prop(self, "feedback_size_main")
@@ -261,7 +297,8 @@ class Archipack_Pref(AddonPreferences):
col.label(text="Manipulators:")
col.prop(self, "arrow_size")
col.prop(self, "handle_size")
- # layout.operator("archipack.render_thumbs")
+ col.prop(self, "text_size")
+ col.prop(self, "constant_handle_size")
# ----------------------------------------------------
# Archipack panels
@@ -273,7 +310,7 @@ class TOOLS_PT_Archipack_Tools(Panel):
bl_idname = "TOOLS_PT_Archipack_Tools"
bl_space_type = "VIEW_3D"
bl_region_type = "TOOLS"
- bl_category = "Tools"
+ # bl_category = "Tools"
bl_context = "objectmode"
@classmethod
@@ -284,23 +321,16 @@ class TOOLS_PT_Archipack_Tools(Panel):
wm = context.window_manager
layout = self.layout
box = layout.box()
- box.label("Auto boolean")
+ box.label(text="Auto boolean")
box.operator("archipack.auto_boolean", text="AutoBoolean", icon='AUTO').mode = 'HYBRID'
- box = layout.box()
- box.label("Rendering")
- box.prop(wm.archipack, 'render_type', text="")
- box.operator("archipack.render", icon='RENDER_STILL')
- box = layout.box()
- box.label("Render presets Thumbnails")
- box.operator("archipack.render_thumbs", icon='ERROR')
class TOOLS_PT_Archipack_Create(Panel):
- bl_label = "Add Archipack"
+ bl_label = "Archipack"
bl_idname = "TOOLS_PT_Archipack_Create"
bl_space_type = "VIEW_3D"
bl_region_type = "TOOLS"
- bl_category = "Create"
+ # bl_category = "Create"
bl_context = "objectmode"
@classmethod
@@ -314,7 +344,7 @@ class TOOLS_PT_Archipack_Create(Panel):
layout = self.layout
row = layout.row(align=True)
box = row.box()
- box.label("Objects")
+ box.label(text="Objects")
row = box.row(align=True)
row.operator("archipack.window_preset_menu",
text="Window",
@@ -454,25 +484,6 @@ def menu_func(self, context):
draw_menu(self, context)
-# ----------------------------------------------------
-# Datablock to store global addon variables
-# ----------------------------------------------------
-
-
-class archipack_data(PropertyGroup):
- render_type = EnumProperty(
- items=(
- ('1', "Draw over", "Draw over last rendered image"),
- ('2', "OpenGL", ""),
- ('3', "Animation OpenGL", ""),
- ('4', "Image", "Render image and draw over"),
- ('5', "Animation", "Draw on each frame")
- ),
- name="Render type",
- description="Render method"
- )
-
-
def register():
global icons_collection
icons = previews.new()
@@ -481,8 +492,6 @@ def register():
name, ext = os.path.splitext(icon)
icons.load(name, os.path.join(icons_dir, icon), 'IMAGE')
icons_collection["main"] = icons
-
- archipack_progressbar.register()
archipack_material.register()
archipack_snap.register()
archipack_manipulator.register()
@@ -498,11 +507,9 @@ def register():
archipack_truss.register()
archipack_floor.register()
archipack_rendering.register()
-
- bpy.utils.register_class(archipack_data)
- WindowManager.archipack = PointerProperty(type=archipack_data)
bpy.utils.register_class(Archipack_Pref)
- update_panel(None, bpy.context)
+ bpy.utils.register_class(TOOLS_PT_Archipack_Tools)
+ bpy.utils.register_class(TOOLS_PT_Archipack_Create)
bpy.utils.register_class(ARCHIPACK_MT_create)
bpy.types.VIEW3D_MT_mesh_add.append(menu_func)
@@ -515,7 +522,6 @@ def unregister():
bpy.utils.unregister_class(TOOLS_PT_Archipack_Tools)
bpy.utils.unregister_class(TOOLS_PT_Archipack_Create)
bpy.utils.unregister_class(Archipack_Pref)
- archipack_progressbar.unregister()
archipack_material.unregister()
archipack_snap.unregister()
archipack_manipulator.unregister()
@@ -532,9 +538,6 @@ def unregister():
archipack_floor.unregister()
archipack_rendering.unregister()
- bpy.utils.unregister_class(archipack_data)
- del WindowManager.archipack
-
for icons in icons_collection.values():
previews.remove(icons)
icons_collection.clear()
diff --git a/archipack/archipack_2d.py b/archipack/archipack_2d.py
index 0078ae3c..e286e730 100644
--- a/archipack/archipack_2d.py
+++ b/archipack/archipack_2d.py
@@ -253,10 +253,10 @@ class Line(Projection):
t: param t of intersection on current line
"""
c = line.cross_z
- d = self.v * c
+ d = self.v.dot(c)
if d == 0:
return False, 0, 0
- t = (c * (line.p - self.p)) / d
+ t = c.dot(line.p - self.p) / d
return True, self.lerp(t), t
def intersect_ext(self, line):
@@ -264,13 +264,13 @@ class Line(Projection):
same as intersect, but return param t on both lines
"""
c = line.cross_z
- d = self.v * c
+ d = self.v.dot(c)
if d == 0:
return False, 0, 0, 0
dp = line.p - self.p
c2 = self.cross_z
- u = (c * dp) / d
- v = (c2 * dp) / d
+ u = c.dot(dp) / d
+ v = c2.dot(dp) / d
return u > 0 and v > 0 and u < 1 and v < 1, self.lerp(u), u, v
def point_sur_segment(self, pt):
@@ -284,7 +284,7 @@ class Line(Projection):
if dl == 0:
return dp.length < 0.00001, 0, 0
d = (self.v.x * dp.y - self.v.y * dp.x) / dl
- t = (self.v * dp) / (dl * dl)
+ t = self.v.dot(dp) / (dl * dl)
return t > 0 and t < 1, d, t
def steps(self, len):
@@ -328,7 +328,7 @@ class Line(Projection):
self.v = Matrix([
[ca, -sa],
[sa, ca]
- ]) * self.v
+ ]) @ self.v
return self
def scale(self, length):
@@ -354,8 +354,8 @@ class Line(Projection):
x, y, z = p
spline.points[i].co = (x, y, 0, 1)
curve_obj = bpy.data.objects.new('LINE', curve)
- context.scene.objects.link(curve_obj)
- curve_obj.select = True
+ context.scene.collection.objects.link(curve_obj)
+ curve_obj.select_set(state=True)
def make_offset(self, offset, last=None):
"""
@@ -399,13 +399,13 @@ class Line(Projection):
# intersect line / line
# 1 line -> 2 line
c = line.cross_z
- d = last.v * c
+ d = last.v.dot(c)
if d == 0:
return line
v = line.p - last.p
- t = (c * v) / d
+ t = c.dot(v) / d
c2 = last.cross_z
- u = (c2 * v) / d
+ u = c2.dot(v) / d
# intersect past this segment end
# or before last segment start
# print("u:%s t:%s" % (u, t))
@@ -431,9 +431,9 @@ class Circle(Projection):
def intersect(self, line):
v = line.p - self.c
- A = line.v * line.v
- B = 2 * v * line.v
- C = v * v - self.r2
+ A = line.v.dot(line.v)
+ B = 2 * v.dot(line.v)
+ C = v.dot(v) - self.r2
d = B * B - 4 * A * C
if A <= 0.0000001 or d < 0:
# dosent intersect, find closest point of line
@@ -549,7 +549,7 @@ class Arc(Circle):
u = self.p0 - self.p1
v = p0 - self.p1
scale, rM = self.scale_rot_matrix(u, v)
- self.c = self.p1 + rM * (self.c - self.p1)
+ self.c = self.p1 + rM @ (self.c - self.p1)
self.r *= scale
self.r2 = self.r * self.r
dp = p0 - self.c
@@ -566,7 +566,7 @@ class Arc(Circle):
v = p1 - p0
scale, rM = self.scale_rot_matrix(u, v)
- self.c = p0 + rM * (self.c - p0)
+ self.c = p0 + rM @ (self.c - p0)
self.r *= scale
self.r2 = self.r * self.r
dp = p0 - self.c
@@ -730,7 +730,7 @@ class Arc(Circle):
[sa, ca]
])
p0 = self.p0
- self.c = p0 + rM * (self.c - p0)
+ self.c = p0 + rM @ (self.c - p0)
dp = p0 - self.c
self.a0 = atan2(dp.y, dp.x)
return self
@@ -842,8 +842,8 @@ class Arc(Circle):
x, y = p
spline.points[i].co = (x, y, 0, 1)
curve_obj = bpy.data.objects.new('ARC', curve)
- context.scene.objects.link(curve_obj)
- curve_obj.select = True
+ context.scene.collection.objects.link(curve_obj)
+ curve_obj.select_set(state=True)
class Line3d(Line):
diff --git a/archipack/archipack_autoboolean.py b/archipack/archipack_autoboolean.py
index 10b8c5ce..ad0e28d8 100644
--- a/archipack/archipack_autoboolean.py
+++ b/archipack/archipack_autoboolean.py
@@ -38,12 +38,11 @@ class ArchipackBoolManager():
- mixed: merge holes with boolean and use result on wall
may be slow, but is robust
"""
- def __init__(self, mode, solver_mode='CARVE'):
+ def __init__(self, mode):
"""
mode in 'ROBUST', 'INTERACTIVE', 'HYBRID'
"""
self.mode = mode
- self.solver_mode = solver_mode
# internal variables
self.itM = None
self.min_x = 0
@@ -69,7 +68,7 @@ class ArchipackBoolManager():
self.min_z + 0.5 * (self.max_z - self.min_z)))
def _contains(self, pt):
- p = self.itM * pt
+ p = self.itM @ pt
return (p.x >= self.min_x and p.x <= self.max_x and
p.y >= self.min_y and p.y <= self.max_y and
p.z >= self.min_z and p.z <= self.max_z)
@@ -108,7 +107,7 @@ class ArchipackBoolManager():
hole.display_type = 'WIRE'
hole.hide_render = True
hole.hide_select = True
- hole.select = True
+ hole.select_set(state=True)
hole.cycles_visibility.camera = False
hole.cycles_visibility.diffuse = False
hole.cycles_visibility.glossy = False
@@ -135,7 +134,7 @@ class ArchipackBoolManager():
if d is not None:
if (self.itM is not None and (
self._contains(o.location) or
- self._contains(o.matrix_world * Vector((0, 0, 0.5 * d.z))))
+ self._contains(o.matrix_world @ Vector((0, 0, 0.5 * d.z))))
):
if self.mode != 'ROBUST':
hole = d.interactive_hole(context, o)
@@ -172,7 +171,7 @@ class ArchipackBoolManager():
sort hole from center to borders by distance from center
may improve nested booleans
"""
- center = wall.matrix_world * self.center
+ center = wall.matrix_world @ self.center
holes = [(o, (o.matrix_world.translation - center).length) for o in holes]
self.quicksort(holes)
return [o[0] for o in holes]
@@ -181,17 +180,12 @@ class ArchipackBoolManager():
# print("difference %s" % (hole.name))
m = basis.modifiers.new('AutoBoolean', 'BOOLEAN')
m.operation = 'DIFFERENCE'
- if solver is None:
- m.solver = self.solver_mode
- else:
- m.solver = solver
m.object = hole
def union(self, basis, hole):
# print("union %s" % (hole.name))
m = basis.modifiers.new('AutoMerge', 'BOOLEAN')
m.operation = 'UNION'
- m.solver = self.solver_mode
m.object = hole
def remove_modif_and_object(self, context, o, to_delete):
@@ -202,7 +196,7 @@ class ArchipackBoolManager():
m.object = None
o.modifiers.remove(m)
if h is not None:
- context.scene.objects.unlink(h)
+ context.scene.collection.objects.unlink(h)
bpy.data.objects.remove(h, do_unlink=True)
# Mixed
@@ -210,7 +204,7 @@ class ArchipackBoolManager():
# print("create_merge_basis")
h = bpy.data.meshes.new("AutoBoolean")
hole_obj = bpy.data.objects.new("AutoBoolean", h)
- context.scene.objects.link(hole_obj)
+ context.scene.collection.objects.link(hole_obj)
hole_obj['archipack_hybridhole'] = True
if wall.parent is not None:
hole_obj.parent = wall.parent
@@ -254,7 +248,6 @@ class ArchipackBoolManager():
m = wall.modifiers.get("AutoMixedBoolean")
if m is None:
m = wall.modifiers.new('AutoMixedBoolean', 'BOOLEAN')
- m.solver = self.solver_mode
m.operation = 'DIFFERENCE'
if m.object is None:
@@ -306,7 +299,7 @@ class ArchipackBoolManager():
to_delete.append([m, h])
# remove modifier and holes not found in new list
self.remove_modif_and_object(context, hole_obj, to_delete)
- context.scene.objects.unlink(hole_obj)
+ # context.scene.collection.objects.unlink(hole_obj)
bpy.data.objects.remove(hole_obj, do_unlink=True)
to_delete = []
@@ -388,12 +381,12 @@ class ArchipackBoolManager():
# to support "revival" of applied modifiers
m = wall.modifiers.get("Wall")
if m is None:
- wall.select = True
- context.scene.objects.active = wall
+ wall.select_set(state=True)
+ context.view_layer.objects.active = wall
wall.data.archipack_wall2[0].update(context)
bpy.ops.object.select_all(action='DESELECT')
- context.scene.objects.active = None
+ context.view_layer.objects.active = None
childs = []
holes = []
# get wall bounds to find what's inside
@@ -429,19 +422,19 @@ class ArchipackBoolManager():
# parenting childs to wall reference point
if wall.parent is None:
x, y, z = wall.bound_box[0]
- context.scene.cursor_location = wall.matrix_world * Vector((x, y, z))
+ context.scene.cursor_location = wall.matrix_world @ Vector((x, y, z))
# fix issue #9
- context.scene.objects.active = wall
+ context.view_layer.objects.active = wall
bpy.ops.archipack.reference_point()
else:
- wall.parent.select = True
- context.scene.objects.active = wall.parent
+ wall.parent.select_set(state=True)
+ context.view_layer.objects.active = wall.parent
- wall.select = True
+ wall.select_set(state=True)
for o in childs:
if 'archipack_robusthole' in o:
o.hide_select = False
- o.select = True
+ o.select_set(state=True)
bpy.ops.archipack.parent_to_reference()
@@ -499,7 +492,6 @@ class ArchipackBoolManager():
if m is None:
m = wall.modifiers.new('AutoMixedBoolean', 'BOOLEAN')
m.operation = 'DIFFERENCE'
- m.solver = self.solver_mode
if m.object is None:
hole_obj = self.create_merge_basis(context, wall)
@@ -513,21 +505,21 @@ class ArchipackBoolManager():
# parenting childs to wall reference point
if wall.parent is None:
x, y, z = wall.bound_box[0]
- context.scene.cursor_location = wall.matrix_world * Vector((x, y, z))
+ context.scene.cursor_location = wall.matrix_world @ Vector((x, y, z))
# fix issue #9
- context.scene.objects.active = wall
+ context.view_layer.objects.active = wall
bpy.ops.archipack.reference_point()
else:
- context.scene.objects.active = wall.parent
+ context.view_layer.objects.active = wall.parent
if hole_obj is not None:
- hole_obj.select = True
+ hole_obj.select_set(state=True)
- wall.select = True
- o.select = True
+ wall.select_set(state=True)
+ o.select_set(state=True)
bpy.ops.archipack.parent_to_reference()
- wall.select = True
- context.scene.objects.active = wall
+ wall.select_set(state=True)
+ context.view_layer.objects.active = wall
if "archipack_wall2" in wall.data:
d = wall.data.archipack_wall2[0]
g = d.get_generator()
@@ -545,7 +537,7 @@ class ARCHIPACK_OT_single_boolean(Operator):
bl_description = "Add single boolean for doors and windows"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- mode = EnumProperty(
+ mode : EnumProperty(
name="Mode",
items=(
('INTERACTIVE', 'INTERACTIVE', 'Interactive, fast but may fail', 0),
@@ -554,7 +546,7 @@ class ARCHIPACK_OT_single_boolean(Operator):
),
default='HYBRID'
)
- solver_mode = EnumProperty(
+ solver_mode : EnumProperty(
name="Solver",
items=(
('CARVE', 'CARVE', 'Slow but robust (could be slow in hybrid mode with many holes)', 0),
@@ -583,14 +575,14 @@ class ARCHIPACK_OT_single_boolean(Operator):
def execute(self, context):
if context.mode == "OBJECT":
wall = context.active_object
- manager = ArchipackBoolManager(mode=self.mode, solver_mode=self.solver_mode)
+ manager = ArchipackBoolManager(mode=self.mode)
for o in context.selected_objects:
if o != wall:
manager.singleboolean(context, wall, o)
+ o.select_set(state=False)
break
- o.select = False
- wall.select = True
- context.scene.objects.active = wall
+ wall.select_set(state=True)
+ context.view_layer.objects.active = wall
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -603,7 +595,7 @@ class ARCHIPACK_OT_auto_boolean(Operator):
bl_description = "Automatic boolean for doors and windows"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- mode = EnumProperty(
+ mode : EnumProperty(
name="Mode",
items=(
('INTERACTIVE', 'INTERACTIVE', 'Interactive, fast but may fail', 0),
@@ -612,14 +604,6 @@ class ARCHIPACK_OT_auto_boolean(Operator):
),
default='HYBRID'
)
- solver_mode = EnumProperty(
- name="Solver",
- items=(
- ('CARVE', 'CARVE', 'Slow but robust (could be slow in hybrid mode with many holes)', 0),
- ('BMESH', 'BMESH', 'Fast but more prone to errors', 1)
- ),
- default='BMESH'
- )
def draw(self, context):
layout = self.layout
@@ -629,22 +613,22 @@ class ARCHIPACK_OT_auto_boolean(Operator):
def execute(self, context):
if context.mode == "OBJECT":
- manager = ArchipackBoolManager(mode=self.mode, solver_mode=self.solver_mode)
- active = context.scene.objects.active
+ manager = ArchipackBoolManager(mode=self.mode)
+ active = context.view_layer.objects.active
walls = [wall for wall in context.selected_objects if not manager.filter_wall(wall)]
bpy.ops.object.select_all(action='DESELECT')
for wall in walls:
manager.autoboolean(context, wall)
bpy.ops.object.select_all(action='DESELECT')
- wall.select = True
- context.scene.objects.active = wall
+ wall.select_set(state=True)
+ context.view_layer.objects.active = wall
if wall.data is not None and 'archipack_wall2' in wall.data:
bpy.ops.archipack.wall2_manipulate('EXEC_DEFAULT')
# reselect walls
bpy.ops.object.select_all(action='DESELECT')
for wall in walls:
- wall.select = True
- context.scene.objects.active = active
+ wall.select_set(state=True)
+ context.view_layer.objects.active = active
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -668,13 +652,13 @@ class ARCHIPACK_OT_generate_hole(Operator):
self.report({'WARNING'}, "Archipack: active object must be a door, a window or a roof")
return {'CANCELLED'}
bpy.ops.object.select_all(action='DESELECT')
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
hole = manager._generate_hole(context, o)
manager.prepare_hole(hole)
- hole.select = False
- o.select = True
- context.scene.objects.active = o
+ hole.select_set(state=False)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
diff --git a/archipack/archipack_cutter.py b/archipack/archipack_cutter.py
index 2ce37d4c..d46dd58f 100644
--- a/archipack/archipack_cutter.py
+++ b/archipack/archipack_cutter.py
@@ -160,7 +160,7 @@ class CutterGenerator():
"""
move shape fromTM into toTM coordsys
"""
- dp = (toTM.inverted() * fromTM.translation).to_2d()
+ dp = (toTM.inverted() @ fromTM.translation).to_2d()
da = toTM.row[1].to_2d().angle_signed(fromTM.row[1].to_2d())
ca = cos(da)
sa = sin(da)
@@ -169,7 +169,7 @@ class CutterGenerator():
[sa, ca]
])
for s in self.segs:
- tp = (rM * s.p0) - s.p0 + dp
+ tp = (rM @ s.p0) - s.p0 + dp
s.rotate(da)
s.translate(tp)
@@ -519,7 +519,7 @@ class CutAbleGenerator():
f.calc_center_median().to_2d(),
segs=segs)]
if len(f_geom) > 0:
- bmesh.ops.delete(bm, geom=f_geom, context=5)
+ bmesh.ops.delete(bm, geom=f_geom, context='FACES')
def cut_boundary(self, bm, cutable, offset={'DEFAULT': 0}):
o_keys = offset.keys()
@@ -545,7 +545,7 @@ class CutAbleGenerator():
f_geom = [f for f in bm.faces
if not cutable.inside(f.calc_center_median().to_2d())]
if len(f_geom) > 0:
- bmesh.ops.delete(bm, geom=f_geom, context=5)
+ bmesh.ops.delete(bm, geom=f_geom, context='FACES')
def update_hole(self, context):
@@ -562,14 +562,14 @@ class ArchipackCutterPart():
Childs MUST define
-type EnumProperty
"""
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
max=1000.0,
default=2.0,
update=update_hole
)
- a0 = FloatProperty(
+ a0 : FloatProperty(
name="Angle",
min=-2 * pi,
max=2 * pi,
@@ -577,7 +577,7 @@ class ArchipackCutterPart():
subtype='ANGLE', unit='ROTATION',
update=update_hole
)
- offset = FloatProperty(
+ offset : FloatProperty(
name="Offset",
min=0,
default=0,
@@ -617,28 +617,28 @@ def update_manipulators(self, context):
class ArchipackCutter():
- n_parts = IntProperty(
+ n_parts : IntProperty(
name="Parts",
min=1,
default=1, update=update_manipulators
)
- z = FloatProperty(
+ z : FloatProperty(
name="dumb z",
description="Dumb z for manipulator placeholder",
default=0.01,
options={'SKIP_SAVE'}
)
- user_defined_path = StringProperty(
+ user_defined_path : StringProperty(
name="User defined",
update=update_path
)
- user_defined_resolution = IntProperty(
+ user_defined_resolution : IntProperty(
name="Resolution",
min=1,
max=128,
default=12, update=update_path
)
- operation = EnumProperty(
+ operation : EnumProperty(
items=(
('DIFFERENCE', 'Difference', 'Cut inside part', 0),
('INTERSECTION', 'Intersection', 'Keep inside part', 1)
@@ -646,16 +646,16 @@ class ArchipackCutter():
default='DIFFERENCE',
update=update_operation
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
)
# UI layout related
- parts_expand = BoolProperty(
+ parts_expand : BoolProperty(
default=False
)
- closed = BoolProperty(
+ closed : BoolProperty(
description="keep closed to be wall snap manipulator compatible",
options={'SKIP_SAVE'},
default=True
@@ -731,18 +731,18 @@ class ArchipackCutter():
# since this can lower points count by a resolution factor
# use normalized to handle non linear t
if resolution == 0:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
v = (p1.co - p0.co).normalized()
d1 = (p0.handle_right - p0.co).normalized()
d2 = (p1.co - p1.handle_left).normalized()
if d1 == v and d2 == v:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
- seg = interpolate_bezier(wM * p0.co,
- wM * p0.handle_right,
- wM * p1.handle_left,
- wM * p1.co,
+ seg = interpolate_bezier(wM @ p0.co,
+ wM @ p0.handle_right,
+ wM @ p1.handle_left,
+ wM @ p1.co,
resolution + 1)
for i in range(resolution):
pts.append(seg[i].to_3d())
@@ -768,7 +768,7 @@ class ArchipackCutter():
def from_spline(self, context, wM, resolution, spline):
pts = []
if spline.type == 'POLY':
- pts = [wM * p.co.to_3d() for p in spline.points]
+ pts = [wM @ p.co.to_3d() for p in spline.points]
if spline.use_cyclic_u:
pts.append(pts[0])
elif spline.type == 'BEZIER':
@@ -783,21 +783,16 @@ class ArchipackCutter():
self.interpolate_bezier(pts, wM, p0, p1, resolution)
pts.append(pts[0])
else:
- pts.append(wM * points[-1].co)
+ pts.append(wM @ points[-1].co)
if self.is_cw(pts) == (self.operation == 'INTERSECTION'):
pts = list(reversed(pts))
- pt = wM.inverted() * pts[0]
+ pt = wM.inverted() @ pts[0]
# pretranslate
o = self.find_in_selection(context, self.auto_update)
- o.matrix_world = wM * Matrix([
- [1, 0, 0, pt.x],
- [0, 1, 0, pt.y],
- [0, 0, 1, pt.z],
- [0, 0, 0, 1]
- ])
+ o.matrix_world = wM @ Matrix.Translation(pt)
self.auto_update = False
self.from_points(pts)
self.auto_update = True
@@ -912,7 +907,7 @@ class ArchipackCutter():
def manipulable_setup(self, context):
self.manipulable_disable(context)
- o = context.active_object
+ o = context.object
n_parts = self.n_parts + 1
diff --git a/archipack/archipack_door.py b/archipack/archipack_door.py
index 3e85cf31..9c63082b 100644
--- a/archipack/archipack_door.py
+++ b/archipack/archipack_door.py
@@ -40,7 +40,7 @@ from .panel import Panel as DoorPanel
from .archipack_handle import create_handle, door_handle_horizontal_01
from .archipack_manipulator import Manipulable
from .archipack_preset import ArchipackPreset, PresetMenuOperator
-from .archipack_object import ArchipackObject, ArchipackCreateTool, ArchpackDrawTool
+from .archipack_object import ArchipackObject, ArchipackCreateTool, ArchipackDrawTool
from .archipack_gl import FeedbackPanel
from .archipack_keymaps import Keymaps
@@ -60,83 +60,83 @@ def update_childs(self, context):
class archipack_door_panel(ArchipackObject, PropertyGroup):
- x = FloatProperty(
+ x : FloatProperty(
name='Width',
min=0.25,
default=100.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='Width'
)
- y = FloatProperty(
+ y : FloatProperty(
name='Depth',
min=0.001,
default=0.02, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='depth'
)
- z = FloatProperty(
+ z : FloatProperty(
name='Height',
min=0.1,
default=2.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='height'
)
- direction = IntProperty(
+ direction : IntProperty(
name="Direction",
min=0,
max=1,
description="open direction"
)
- model = IntProperty(
+ model : IntProperty(
name="Model",
min=0,
max=3,
default=0,
description="Model"
)
- chanfer = FloatProperty(
+ chanfer : FloatProperty(
name='Bevel',
min=0.001,
default=0.005, precision=3,
unit='LENGTH', subtype='DISTANCE',
description='chanfer'
)
- panel_spacing = FloatProperty(
+ panel_spacing : FloatProperty(
name='Spacing',
min=0.001,
default=0.1, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance between panels'
)
- panel_bottom = FloatProperty(
+ panel_bottom : FloatProperty(
name='Bottom',
min=0.0,
default=0.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance from bottom'
)
- panel_border = FloatProperty(
+ panel_border : FloatProperty(
name='Border',
min=0.001,
default=0.2, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance from border'
)
- panels_x = IntProperty(
+ panels_x : IntProperty(
name="# h",
min=1,
max=50,
default=1,
description="panels h"
)
- panels_y = IntProperty(
+ panels_y : IntProperty(
name="# v",
min=1,
max=50,
default=1,
description="panels v"
)
- panels_distrib = EnumProperty(
+ panels_distrib : EnumProperty(
name='distribution',
items=(
('REGULAR', 'Regular', '', 0),
@@ -144,7 +144,7 @@ class archipack_door_panel(ArchipackObject, PropertyGroup):
),
default='REGULAR'
)
- handle = EnumProperty(
+ handle : EnumProperty(
name='Shape',
items=(
('NONE', 'No handle', '', 0),
@@ -559,7 +559,7 @@ class archipack_door_panel(ArchipackObject, PropertyGroup):
def remove_handle(self, context, o):
handle = self.find_handle(o)
if handle is not None:
- context.scene.objects.unlink(handle)
+ context.scene.collection.objects.unlink(handle)
bpy.data.objects.remove(handle, do_unlink=True)
def update(self, context):
@@ -584,7 +584,7 @@ class ARCHIPACK_PT_door_panel(Panel):
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
# bl_context = 'object'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -606,82 +606,82 @@ class ARCHIPACK_OT_door_panel(Operator):
bl_description = "Door model 1"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- x = FloatProperty(
+ x : FloatProperty(
name='Width',
min=0.1,
default=0.80, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='Width'
)
- z = FloatProperty(
+ z : FloatProperty(
name='Height',
min=0.1,
default=2.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='height'
)
- y = FloatProperty(
+ y : FloatProperty(
name='Depth',
min=0.001,
default=0.02, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='Depth'
)
- direction = IntProperty(
+ direction : IntProperty(
name="Direction",
min=0,
max=1,
description="open direction"
)
- model = IntProperty(
+ model : IntProperty(
name="Model",
min=0,
max=3,
description="panel type"
)
- chanfer = FloatProperty(
+ chanfer : FloatProperty(
name='Bevel',
min=0.001,
default=0.005, precision=3,
unit='LENGTH', subtype='DISTANCE',
description='chanfer'
)
- panel_spacing = FloatProperty(
+ panel_spacing : FloatProperty(
name='Spacing',
min=0.001,
default=0.1, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance between panels'
)
- panel_bottom = FloatProperty(
+ panel_bottom : FloatProperty(
name='Bottom',
min=0.0,
default=0.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance from bottom'
)
- panel_border = FloatProperty(
+ panel_border : FloatProperty(
name='Border',
min=0.001,
default=0.2, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance from border'
)
- panels_x = IntProperty(
+ panels_x : IntProperty(
name="# h",
min=1,
max=50,
default=1,
description="panels h"
)
- panels_y = IntProperty(
+ panels_y : IntProperty(
name="# v",
min=1,
max=50,
default=1,
description="panels v"
)
- panels_distrib = EnumProperty(
+ panels_distrib : EnumProperty(
name='Distribution',
items=(
('REGULAR', 'Regular', '', 0),
@@ -689,7 +689,7 @@ class ARCHIPACK_OT_door_panel(Operator):
),
default='REGULAR'
)
- handle = EnumProperty(
+ handle : EnumProperty(
name='Shape',
items=(
('NONE', 'No handle', '', 0),
@@ -697,14 +697,14 @@ class ARCHIPACK_OT_door_panel(Operator):
),
default='BOTH'
)
- material = StringProperty(
+ material : StringProperty(
default=""
)
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
"""
@@ -727,7 +727,7 @@ class ARCHIPACK_OT_door_panel(Operator):
d.panels_x = self.panels_x
d.panels_y = self.panels_y
d.handle = self.handle
- context.scene.objects.link(o)
+ context.scene.collection.objects.link(o)
o.lock_location[0] = True
o.lock_location[1] = True
o.lock_location[2] = True
@@ -736,8 +736,8 @@ class ARCHIPACK_OT_door_panel(Operator):
o.lock_scale[0] = True
o.lock_scale[1] = True
o.lock_scale[2] = True
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
m = o.archipack_material.add()
m.category = "door"
m.material = self.material
@@ -751,8 +751,8 @@ class ARCHIPACK_OT_door_panel(Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -769,14 +769,14 @@ class ARCHIPACK_OT_select_parent(Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def execute(self, context):
if context.mode == "OBJECT":
if context.active_object is not None and context.active_object.parent is not None:
bpy.ops.object.select_all(action="DESELECT")
- context.active_object.parent.select = True
- context.scene.objects.active = context.active_object.parent
+ context.active_object.parent.select_set(state=True)
+ context.view_layer.objects.active = context.active_object.parent
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -789,117 +789,117 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
parent parametric object
create/remove/update her own childs
"""
- x = FloatProperty(
+ x : FloatProperty(
name='Width',
min=0.25,
default=100.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='Width', update=update,
)
- y = FloatProperty(
+ y : FloatProperty(
name='Depth',
min=0.1,
default=0.20, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='Depth', update=update,
)
- z = FloatProperty(
+ z : FloatProperty(
name='Height',
min=0.1,
default=2.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='height', update=update,
)
- frame_x = FloatProperty(
+ frame_x : FloatProperty(
name='Width',
min=0,
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame width', update=update,
)
- frame_y = FloatProperty(
+ frame_y : FloatProperty(
name='Depth',
default=0.03, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame depth', update=update,
)
- direction = IntProperty(
+ direction : IntProperty(
name="Direction",
min=0,
max=1,
description="open direction", update=update,
)
- door_y = FloatProperty(
+ door_y : FloatProperty(
name='Depth',
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='depth', update=update,
)
- door_offset = FloatProperty(
+ door_offset : FloatProperty(
name='Offset',
min=0,
default=0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='offset', update=update,
)
- model = IntProperty(
+ model : IntProperty(
name="Model",
min=0,
max=3,
default=0,
description="Model", update=update,
)
- n_panels = IntProperty(
+ n_panels : IntProperty(
name="Panels",
min=1,
max=2,
default=1,
description="number of panels", update=update
)
- chanfer = FloatProperty(
+ chanfer : FloatProperty(
name='Bevel',
min=0.001,
default=0.005, precision=3, step=0.01,
unit='LENGTH', subtype='DISTANCE',
description='chanfer', update=update_childs,
)
- panel_spacing = FloatProperty(
+ panel_spacing : FloatProperty(
name='Spacing',
min=0.001,
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='distance between panels', update=update_childs,
)
- panel_bottom = FloatProperty(
+ panel_bottom : FloatProperty(
name='Bottom',
min=0.0,
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='distance from bottom', update=update_childs,
)
- panel_border = FloatProperty(
+ panel_border : FloatProperty(
name='Border',
min=0.001,
default=0.2, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='distance from border', update=update_childs,
)
- panels_x = IntProperty(
+ panels_x : IntProperty(
name="# h",
min=1,
max=50,
default=1,
description="panels h", update=update_childs,
)
- panels_y = IntProperty(
+ panels_y : IntProperty(
name="# v",
min=1,
max=50,
default=1,
description="panels v", update=update_childs,
)
- panels_distrib = EnumProperty(
+ panels_distrib : EnumProperty(
name='Distribution',
items=(
('REGULAR', 'Regular', '', 0),
@@ -907,7 +907,7 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
),
default='REGULAR', update=update_childs,
)
- handle = EnumProperty(
+ handle : EnumProperty(
name='Handle',
items=(
('NONE', 'No handle', '', 0),
@@ -915,19 +915,19 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
),
default='BOTH', update=update_childs,
)
- hole_margin = FloatProperty(
+ hole_margin : FloatProperty(
name='Hole margin',
min=0.0,
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='how much hole surround wall'
)
- flip = BoolProperty(
+ flip : BoolProperty(
default=False,
update=update,
description='flip outside and outside material of hole'
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update
@@ -1032,13 +1032,13 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
if archipack_door_panel.filter(child):
self.remove_handle(context, child)
to_remove -= 1
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child, do_unlink=True)
def remove_handle(self, context, o):
handle = self.find_handle(o)
if handle is not None:
- context.scene.objects.unlink(handle)
+ context.scene.collection.objects.unlink(handle)
bpy.data.objects.remove(handle, do_unlink=True)
def create_childs(self, context, o):
@@ -1112,7 +1112,7 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
id = c_names.index(c.data.name)
except:
self.remove_handle(context, c)
- context.scene.objects.unlink(c)
+ context.scene.collection.objects.unlink(c)
bpy.data.objects.remove(c, do_unlink=True)
# children ordering may not be the same, so get the right l_childs order
@@ -1130,7 +1130,7 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
for i, child in enumerate(childs):
if order[i] < 0:
p = bpy.data.objects.new("DoorPanel", child.data)
- context.scene.objects.link(p)
+ context.scene.collection.objects.link(p)
p.lock_location[0] = True
p.lock_location[1] = True
p.lock_location[2] = True
@@ -1158,7 +1158,7 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
# MaterialUtils.add_handle_materials(h)
h.location = handle.location.copy()
elif h is not None:
- context.scene.objects.unlink(h)
+ context.scene.collection.objects.unlink(h)
bpy.data.objects.remove(h, do_unlink=True)
def _synch_hole(self, context, linked, hole):
@@ -1166,7 +1166,7 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
if l_hole is None:
l_hole = bpy.data.objects.new("hole", hole.data)
l_hole['archipack_hole'] = True
- context.scene.objects.link(l_hole)
+ context.scene.collection.objects.link(l_hole)
l_hole.parent = linked
l_hole.matrix_world = linked.matrix_world.copy()
l_hole.location = hole.location.copy()
@@ -1178,8 +1178,8 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
synch childs nodes of linked objects
"""
bpy.ops.object.select_all(action='DESELECT')
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
childs = self.get_childs_panels(context, o)
hole = self.find_hole(o)
bpy.ops.object.select_linked(type='OBDATA')
@@ -1253,8 +1253,8 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
child.matrix_world = o.matrix_world.copy()
else:
child = childs[child_n - 1]
- child.select = True
- context.scene.objects.active = child
+ child.select_set(state=True)
+ context.view_layer.objects.active = child
props = archipack_door_panel.datablock(child)
if props is not None:
props.x = x
@@ -1314,7 +1314,7 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
if hole_obj is None:
m = bpy.data.meshes.new("hole")
hole_obj = bpy.data.objects.new("hole", m)
- context.scene.objects.link(hole_obj)
+ context.scene.collection.objects.link(hole_obj)
hole_obj['archipack_hole'] = True
hole_obj.parent = o
hole_obj.matrix_world = o.matrix_world.copy()
@@ -1339,19 +1339,19 @@ class archipack_door(ArchipackObject, Manipulable, PropertyGroup):
m = bpy.data.meshes.new("hole")
o = bpy.data.objects.new("hole", m)
o['archipack_robusthole'] = True
- context.scene.objects.link(o)
+ context.scene.collection.objects.link(o)
v = Vector((0, 0, 0))
offset = Vector((0, -0.001, 0))
size = Vector((self.x + 2 * self.frame_x, self.z + self.frame_x + 0.001, self.y))
verts = hole.vertices(16, offset, v, v, size, v, 0, 0, shape_z=None, path_type='RECTANGLE')
- verts = [tM * Vector(v) for v in verts]
+ verts = [tM @ Vector(v) for v in verts]
faces = hole.faces(16, path_type='RECTANGLE')
matids = hole.mat(16, 0, 1, path_type='RECTANGLE')
uvs = hole.uv(16, v, v, size, v, 0, 0, 0, 0, path_type='RECTANGLE')
bmed.buildmesh(context, o, verts, faces, matids=matids, uvs=uvs)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return o
@@ -1360,7 +1360,7 @@ class ARCHIPACK_PT_door(Panel):
bl_label = "Door"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1371,7 +1371,7 @@ class ARCHIPACK_PT_door(Panel):
if not archipack_door.filter(o):
return
layout = self.layout
- layout.operator('archipack.door_manipulate', icon='HAND')
+ layout.operator('archipack.door_manipulate', icon='VIEW_PAN')
props = archipack_door.datablock(o)
row = layout.row(align=True)
row.operator('archipack.door', text="Refresh", icon='FILE_REFRESH').mode = 'REFRESH'
@@ -1382,8 +1382,8 @@ class ARCHIPACK_PT_door(Panel):
# box.label(text="Styles")
row = box.row(align=True)
row.operator("archipack.door_preset_menu", text=bpy.types.ARCHIPACK_OT_door_preset_menu.bl_label)
- row.operator("archipack.door_preset", text="", icon='ZOOMIN')
- row.operator("archipack.door_preset", text="", icon='ZOOMOUT').remove_active = True
+ row.operator("archipack.door_preset", text="", icon='ADD')
+ row.operator("archipack.door_preset", text="", icon='REMOVE').remove_active = True
row = layout.row()
box = row.box()
box.label(text="Size")
@@ -1434,82 +1434,82 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
bl_description = "Door"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- x = FloatProperty(
+ x : FloatProperty(
name='width',
min=0.1,
default=0.80, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='Width'
)
- y = FloatProperty(
+ y : FloatProperty(
name='depth',
min=0.1,
default=0.20, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='Depth'
)
- z = FloatProperty(
+ z : FloatProperty(
name='height',
min=0.1,
default=2.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='height'
)
- direction = IntProperty(
+ direction : IntProperty(
name="direction",
min=0,
max=1,
description="open direction"
)
- n_panels = IntProperty(
+ n_panels : IntProperty(
name="panels",
min=1,
max=2,
default=1,
description="number of panels"
)
- chanfer = FloatProperty(
+ chanfer : FloatProperty(
name='chanfer',
min=0.001,
default=0.005, precision=3,
unit='LENGTH', subtype='DISTANCE',
description='chanfer'
)
- panel_spacing = FloatProperty(
+ panel_spacing : FloatProperty(
name='spacing',
min=0.001,
default=0.1, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance between panels'
)
- panel_bottom = FloatProperty(
+ panel_bottom : FloatProperty(
name='bottom',
default=0.0, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance from bottom'
)
- panel_border = FloatProperty(
+ panel_border : FloatProperty(
name='border',
min=0.001,
default=0.2, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='distance from border'
)
- panels_x = IntProperty(
+ panels_x : IntProperty(
name="panels h",
min=1,
max=50,
default=1,
description="panels h"
)
- panels_y = IntProperty(
+ panels_y : IntProperty(
name="panels v",
min=1,
max=50,
default=1,
description="panels v"
)
- panels_distrib = EnumProperty(
+ panels_distrib : EnumProperty(
name='distribution',
items=(
('REGULAR', 'Regular', '', 0),
@@ -1517,7 +1517,7 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
),
default='REGULAR'
)
- handle = EnumProperty(
+ handle : EnumProperty(
name='Shape',
items=(
('NONE', 'No handle', '', 0),
@@ -1525,7 +1525,7 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
),
default='BOTH'
)
- mode = EnumProperty(
+ mode : EnumProperty(
items=(
('CREATE', 'Create', '', 0),
('DELETE', 'Delete', '', 1),
@@ -1556,13 +1556,13 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
d.panels_x = self.panels_x
d.panels_y = self.panels_y
d.handle = self.handle
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.add_material(o)
self.load_preset(d)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return o
def delete(self, context):
@@ -1571,16 +1571,16 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
bpy.ops.archipack.disable_manipulate()
for child in o.children:
if 'archipack_hole' in child:
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child, do_unlink=True)
elif child.data is not None and 'archipack_door_panel' in child.data:
for handle in child.children:
if 'archipack_handle' in handle:
- context.scene.objects.unlink(handle)
+ context.scene.collection.objects.unlink(handle)
bpy.data.objects.remove(handle, do_unlink=True)
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child, do_unlink=True)
- context.scene.objects.unlink(o)
+ context.scene.collection.objects.unlink(o)
bpy.data.objects.remove(o, do_unlink=True)
def update(self, context):
@@ -1593,8 +1593,8 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
if linked != o:
archipack_door.datablock(linked).update(context)
bpy.ops.object.select_all(action="DESELECT")
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
def unique(self, context):
act = context.active_object
@@ -1602,12 +1602,12 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
for o in sel:
if archipack_door.filter(o):
- o.select = True
+ o.select_set(state=True)
for child in o.children:
if 'archipack_hole' in child or (child.data is not None and
'archipack_door_panel' in child.data):
child.hide_select = False
- child.select = True
+ child.select_set(state=True)
if len(context.selected_objects) > 0:
bpy.ops.object.make_single_user(type='SELECTED_OBJECTS', object=True,
obdata=True, material=False, texture=False, animation=False)
@@ -1615,9 +1615,9 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
if 'archipack_hole' in child:
child.hide_select = True
bpy.ops.object.select_all(action="DESELECT")
- context.scene.objects.active = act
+ context.view_layer.objects.active = act
for o in sel:
- o.select = True
+ o.select_set(state=True)
def execute(self, context):
if context.mode == "OBJECT":
@@ -1625,8 +1625,8 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = bpy.context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
elif self.mode == 'DELETE':
self.delete(context)
@@ -1640,14 +1640,14 @@ class ARCHIPACK_OT_door(ArchipackCreateTool, Operator):
return {'CANCELLED'}
-class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
+class ARCHIPACK_OT_door_draw(ArchipackDrawTool, Operator):
bl_idname = "archipack.door_draw"
bl_label = "Draw Doors"
bl_description = "Draw Doors over walls"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- filepath = StringProperty(default="")
+ filepath : StringProperty(default="")
feedback = None
stack = []
object_name = ""
@@ -1659,7 +1659,7 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def draw_callback(self, _self, context):
self.feedback.draw(context)
@@ -1670,32 +1670,32 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
if archipack_door.filter(o):
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
if event.shift:
bpy.ops.archipack.door(mode="UNIQUE")
new_w = o.copy()
new_w.data = o.data
- context.scene.objects.link(new_w)
+ context.scene.collection.objects.link(new_w)
# instance subs
for child in o.children:
if "archipack_hole" not in child:
new_c = child.copy()
new_c.data = child.data
new_c.parent = new_w
- context.scene.objects.link(new_c)
+ context.scene.collection.objects.link(new_c)
# dup handle if any
for c in child.children:
new_h = c.copy()
new_h.data = c.data
new_h.parent = new_c
- context.scene.objects.link(new_h)
+ context.scene.collection.objects.link(new_h)
o = new_w
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
else:
bpy.ops.archipack.door(auto_manipulate=False, filepath=self.filepath)
@@ -1704,8 +1704,8 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
self.object_name = o.name
bpy.ops.archipack.generate_hole('INVOKE_DEFAULT')
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
def modal(self, context, event):
@@ -1722,14 +1722,14 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
# hide hole from raycast
if hole is not None:
- o.hide = True
- hole.hide = True
+ o.hide_viewport = True
+ hole.hide_viewport = True
- res, tM, wall, y = self.mouse_hover_wall(context, event)
+ res, tM, wall, width, y, z_offset = self.mouse_hover_wall(context, event)
if hole is not None:
- o.hide = False
- hole.hide = False
+ o.hide_viewport = False
+ hole.hide_viewport = False
if res and d is not None:
o.matrix_world = tM
@@ -1749,14 +1749,14 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
if event.type in {'LEFTMOUSE', 'RET', 'NUMPAD_ENTER', 'SPACE'}:
if wall is not None:
- context.scene.objects.active = wall
- wall.select = True
+ context.view_layer.objects.active = wall
+ wall.select_set(state=True)
if bpy.ops.archipack.single_boolean.poll():
bpy.ops.archipack.single_boolean()
- wall.select = False
+ wall.select_set(state=False)
# o must be a door here
if d is not None:
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
self.stack.append(o)
self.add_object(context, event)
context.active_object.matrix_world = tM
@@ -1771,9 +1771,9 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
):
if len(self.stack) > 0:
last = self.stack.pop()
- context.scene.objects.active = last
+ context.view_layer.objects.active = last
bpy.ops.archipack.door(mode="DELETE")
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
return {'RUNNING_MODAL'}
if event.value == 'RELEASE':
@@ -1797,11 +1797,11 @@ class ARCHIPACK_OT_door_draw(ArchpackDrawTool, Operator):
# invoke with alt pressed will use current object as basis for linked copy
if self.filepath == '' and archipack_door.filter(context.active_object):
o = context.active_object
- context.scene.objects.active = None
+ context.view_layer.objects.active = None
bpy.ops.object.select_all(action="DESELECT")
if o is not None:
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.add_object(context, event)
self.feedback = FeedbackPanel()
self.feedback.instructions(context, "Draw a door", "Click & Drag over a wall", [
diff --git a/archipack/archipack_fence.py b/archipack/archipack_fence.py
index a94023fd..0196aac8 100644
--- a/archipack/archipack_fence.py
+++ b/archipack/archipack_fence.py
@@ -268,7 +268,7 @@ class FenceGenerator():
co.z *= self.user_defined_post_scale.z
if 'Slope' in g:
co.z += co.y * slope
- verts.append(tM * co)
+ verts.append(tM @ co)
matids += self.user_defined_mat
faces += [tuple([i + f for i in p.vertices]) for p in m.polygons]
uvs += self.user_defined_uvs
@@ -341,7 +341,7 @@ class FenceGenerator():
if s < n_sections:
v1 = subs[s + 1][0].v.normalized()
dir = (v0 + v1).normalized()
- scale = 1 / cos(0.5 * acos(min(1, max(-1, v0 * v1))))
+ scale = 1 / cos(0.5 * acos(min(1, max(-1, v0.dot(v1)))))
for p in profile:
x, y = n.p + scale * p.x * dir
z = zl + p.y + altitude
@@ -556,7 +556,7 @@ class FenceGenerator():
if s < n_sections:
v1 = sections[s + 1][0].v.normalized()
dir = (v0 + v1).normalized()
- scale = min(10, 1 / cos(0.5 * acos(min(1, max(-1, v0 * v1)))))
+ scale = min(10, 1 / cos(0.5 * acos(min(1, max(-1, v0.dot(v1) )))))
for p in profile:
# x, y = n.p + scale * (x_offset + p.x) * dir
x, y = n.p + scale * p.x * dir
@@ -673,7 +673,7 @@ materials_enum = (
class archipack_fence_material(PropertyGroup):
- index = EnumProperty(
+ index : EnumProperty(
items=materials_enum,
default='0',
update=update
@@ -684,7 +684,7 @@ class archipack_fence_material(PropertyGroup):
find witch selected object this instance belongs to
provide support for "copy to selected"
"""
- selected = [o for o in context.selected_objects]
+ selected = context.selected_objects[:]
for o in selected:
props = archipack_fence.datablock(o)
if props:
@@ -700,7 +700,7 @@ class archipack_fence_material(PropertyGroup):
class archipack_fence_part(PropertyGroup):
- type = EnumProperty(
+ type : EnumProperty(
items=(
('S_FENCE', 'Straight fence', '', 0),
('C_FENCE', 'Curved fence', '', 1),
@@ -708,21 +708,21 @@ class archipack_fence_part(PropertyGroup):
default='S_FENCE',
update=update_type
)
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
default=2.0,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.01,
default=0.7,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -730,7 +730,7 @@ class archipack_fence_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- a0 = FloatProperty(
+ a0 : FloatProperty(
name="Start angle",
min=-2 * pi,
max=2 * pi,
@@ -738,13 +738,13 @@ class archipack_fence_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- dz = FloatProperty(
+ dz : FloatProperty(
name="delta z",
default=0,
unit='LENGTH', subtype='DISTANCE'
)
- manipulators = CollectionProperty(type=archipack_manipulator)
+ manipulators : CollectionProperty(type=archipack_manipulator)
def find_datablock_in_selection(self, context):
"""
@@ -783,43 +783,43 @@ class archipack_fence_part(PropertyGroup):
class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
- parts = CollectionProperty(type=archipack_fence_part)
- user_defined_path = StringProperty(
+ parts : CollectionProperty(type=archipack_fence_part)
+ user_defined_path : StringProperty(
name="User defined",
update=update_path
)
- user_defined_spline = IntProperty(
+ user_defined_spline : IntProperty(
name="Spline index",
min=0,
default=0,
update=update_path
)
- user_defined_resolution = IntProperty(
+ user_defined_resolution : IntProperty(
name="Resolution",
min=1,
max=128,
default=12, update=update_path
)
- n_parts = IntProperty(
+ n_parts : IntProperty(
name="Parts",
min=1,
default=1, update=update_manipulators
)
- x_offset = FloatProperty(
+ x_offset : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.01,
default=0.7,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -827,7 +827,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- angle_limit = FloatProperty(
+ angle_limit : FloatProperty(
name="Angle",
min=0,
max=2 * pi,
@@ -835,7 +835,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update_manipulators
)
- shape = EnumProperty(
+ shape : EnumProperty(
items=(
('RECTANGLE', 'Straight', '', 0),
('CIRCLE', 'Curved ', '', 1)
@@ -843,106 +843,106 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
default='RECTANGLE',
update=update
)
- post = BoolProperty(
+ post : BoolProperty(
name='Enable',
default=True,
update=update
)
- post_spacing = FloatProperty(
+ post_spacing : FloatProperty(
name="Spacing",
min=0.1,
default=1.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_x = FloatProperty(
+ post_x : FloatProperty(
name="Width",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_y = FloatProperty(
+ post_y : FloatProperty(
name="Length",
min=0.001, max=1000,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_z = FloatProperty(
+ post_z : FloatProperty(
name="Height",
min=0.001,
default=1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_alt = FloatProperty(
+ post_alt : FloatProperty(
name="Altitude",
default=0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- user_defined_post_enable = BoolProperty(
+ user_defined_post_enable : BoolProperty(
name="User",
update=update,
default=True
)
- user_defined_post = StringProperty(
+ user_defined_post : StringProperty(
name="User defined",
update=update
)
- idmat_post = EnumProperty(
+ idmat_post : EnumProperty(
name="Post",
items=materials_enum,
default='1',
update=update
)
- subs = BoolProperty(
+ subs : BoolProperty(
name='Enable',
default=False,
update=update
)
- subs_spacing = FloatProperty(
+ subs_spacing : FloatProperty(
name="Spacing",
min=0.05,
default=0.10, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_x = FloatProperty(
+ subs_x : FloatProperty(
name="Width",
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_y = FloatProperty(
+ subs_y : FloatProperty(
name="Length",
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_z = FloatProperty(
+ subs_z : FloatProperty(
name="Height",
min=0.001,
default=1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_alt = FloatProperty(
+ subs_alt : FloatProperty(
name="Altitude",
default=0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_offset_x = FloatProperty(
+ subs_offset_x : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_bottom = EnumProperty(
+ subs_bottom : EnumProperty(
name="Bottom",
items=(
('STEP', 'Follow step', '', 0),
@@ -951,78 +951,78 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
default='STEP',
update=update
)
- user_defined_subs_enable = BoolProperty(
+ user_defined_subs_enable : BoolProperty(
name="User",
update=update,
default=True
)
- user_defined_subs = StringProperty(
+ user_defined_subs : StringProperty(
name="User defined",
update=update
)
- idmat_subs = EnumProperty(
+ idmat_subs : EnumProperty(
name="Subs",
items=materials_enum,
default='1',
update=update
)
- panel = BoolProperty(
+ panel : BoolProperty(
name='Enable',
default=True,
update=update
)
- panel_alt = FloatProperty(
+ panel_alt : FloatProperty(
name="Altitude",
default=0.25, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_x = FloatProperty(
+ panel_x : FloatProperty(
name="Width",
min=0.001,
default=0.01, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_z = FloatProperty(
+ panel_z : FloatProperty(
name="Height",
min=0.001,
default=0.6, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_dist = FloatProperty(
+ panel_dist : FloatProperty(
name="Spacing",
min=0.001,
default=0.05, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_offset_x = FloatProperty(
+ panel_offset_x : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- idmat_panel = EnumProperty(
+ idmat_panel : EnumProperty(
name="Panels",
items=materials_enum,
default='2',
update=update
)
- rail = BoolProperty(
+ rail : BoolProperty(
name="Enable",
update=update,
default=False
)
- rail_n = IntProperty(
+ rail_n : IntProperty(
name="#",
default=1,
min=0,
max=31,
update=update
)
- rail_x = FloatVectorProperty(
+ rail_x : FloatVectorProperty(
name="Width",
default=[
0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05,
@@ -1036,7 +1036,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_z = FloatVectorProperty(
+ rail_z : FloatVectorProperty(
name="Height",
default=[
0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05,
@@ -1050,7 +1050,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_offset = FloatVectorProperty(
+ rail_offset : FloatVectorProperty(
name="Offset",
default=[
0, 0, 0, 0, 0, 0, 0, 0,
@@ -1063,7 +1063,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_alt = FloatVectorProperty(
+ rail_alt : FloatVectorProperty(
name="Altitude",
default=[
1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0,
@@ -1076,43 +1076,43 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_mat = CollectionProperty(type=archipack_fence_material)
+ rail_mat : CollectionProperty(type=archipack_fence_material)
- handrail = BoolProperty(
+ handrail : BoolProperty(
name="Enable",
update=update,
default=True
)
- handrail_offset = FloatProperty(
+ handrail_offset : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_alt = FloatProperty(
+ handrail_alt : FloatProperty(
name="Altitude",
default=1.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_extend = FloatProperty(
+ handrail_extend : FloatProperty(
name="Extend",
min=0,
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_slice = BoolProperty(
+ handrail_slice : BoolProperty(
name='Slice',
default=True,
update=update
)
- handrail_slice_right = BoolProperty(
+ handrail_slice_right : BoolProperty(
name='Slice',
default=True,
update=update
)
- handrail_profil = EnumProperty(
+ handrail_profil : EnumProperty(
name="Profil",
items=(
('SQUARE', 'Square', '', 0),
@@ -1122,28 +1122,28 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
default='SQUARE',
update=update
)
- handrail_x = FloatProperty(
+ handrail_x : FloatProperty(
name="Width",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_y = FloatProperty(
+ handrail_y : FloatProperty(
name="Height",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_radius = FloatProperty(
+ handrail_radius : FloatProperty(
name="Radius",
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- idmat_handrail = EnumProperty(
+ idmat_handrail : EnumProperty(
name="Handrail",
items=materials_enum,
default='0',
@@ -1151,25 +1151,25 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
)
# UI layout related
- parts_expand = BoolProperty(
+ parts_expand : BoolProperty(
default=False
)
- rail_expand = BoolProperty(
+ rail_expand : BoolProperty(
default=False
)
- idmats_expand = BoolProperty(
+ idmats_expand : BoolProperty(
default=False
)
- handrail_expand = BoolProperty(
+ handrail_expand : BoolProperty(
default=False
)
- post_expand = BoolProperty(
+ post_expand : BoolProperty(
default=False
)
- panel_expand = BoolProperty(
+ panel_expand : BoolProperty(
default=False
)
- subs_expand = BoolProperty(
+ subs_expand : BoolProperty(
default=False
)
@@ -1178,7 +1178,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
# .auto_update = False
# bulk changes
# .auto_update = True
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
@@ -1226,26 +1226,27 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
# add parts
for i in range(len(self.parts), self.n_parts):
self.parts.add()
-
+ print("setup_manipulators")
self.setup_manipulators()
+ print("update_parts.done")
def interpolate_bezier(self, pts, wM, p0, p1, resolution):
# straight segment, worth testing here
# since this can lower points count by a resolution factor
# use normalized to handle non linear t
if resolution == 0:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
v = (p1.co - p0.co).normalized()
d1 = (p0.handle_right - p0.co).normalized()
d2 = (p1.co - p1.handle_left).normalized()
if d1 == v and d2 == v:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
- seg = interpolate_bezier(wM * p0.co,
- wM * p0.handle_right,
- wM * p1.handle_left,
- wM * p1.co,
+ seg = interpolate_bezier(wM @ p0.co,
+ wM @ p0.handle_right,
+ wM @ p1.handle_left,
+ wM @ p1.co,
resolution + 1)
for i in range(resolution):
pts.append(seg[i].to_3d())
@@ -1264,7 +1265,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
pts = []
if spline.type == 'POLY':
pt = spline.points[0].co
- pts = [wM * p.co.to_3d() for p in spline.points]
+ pts = [wM @ p.co.to_3d() for p in spline.points]
if spline.use_cyclic_u:
pts.append(pts[0])
elif spline.type == 'BEZIER':
@@ -1280,7 +1281,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
self.interpolate_bezier(pts, wM, p0, p1, resolution)
pts.append(pts[0])
else:
- pts.append(wM * points[-1].co)
+ pts.append(wM @ points[-1].co)
auto_update = self.auto_update
self.auto_update = False
@@ -1305,12 +1306,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
self.auto_update = auto_update
- o.matrix_world = tM * Matrix([
- [1, 0, 0, pt.x],
- [0, 1, 0, pt.y],
- [0, 0, 1, pt.z],
- [0, 0, 0, 1]
- ])
+ o.matrix_world = tM @ Matrix.Translation(pt)
def update_path(self, context):
path = context.scene.objects.get(self.user_defined_path)
@@ -1335,7 +1331,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
return g
def update(self, context, manipulable_refresh=False):
-
+ print("update")
o = self.find_in_selection(context, self.auto_update)
if o is None:
@@ -1344,7 +1340,7 @@ class archipack_fence(ArchipackObject, Manipulable, PropertyGroup):
# clean up manipulators before any data model change
if manipulable_refresh:
self.manipulable_disable(context)
-
+ print("update_parts")
self.update_parts()
verts = []
@@ -1465,7 +1461,7 @@ class ARCHIPACK_PT_fence(Panel):
bl_label = "Fence"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1478,13 +1474,13 @@ class ARCHIPACK_PT_fence(Panel):
scene = context.scene
layout = self.layout
row = layout.row(align=True)
- row.operator('archipack.fence_manipulate', icon='HAND')
+ row.operator('archipack.fence_manipulate', icon='VIEW_PAN')
box = layout.box()
# box.label(text="Styles")
row = box.row(align=True)
row.operator("archipack.fence_preset_menu", text=bpy.types.ARCHIPACK_OT_fence_preset_menu.bl_label)
- row.operator("archipack.fence_preset", text="", icon='ZOOMIN')
- row.operator("archipack.fence_preset", text="", icon='ZOOMOUT').remove_active = True
+ row.operator("archipack.fence_preset", text="", icon='ADD')
+ row.operator("archipack.fence_preset", text="", icon='REMOVE').remove_active = True
box = layout.box()
row = box.row(align=True)
row.operator("archipack.fence_curve_update", text="", icon='FILE_REFRESH')
@@ -1619,25 +1615,35 @@ class ARCHIPACK_OT_fence(ArchipackCreateTool, Operator):
bl_options = {'REGISTER', 'UNDO'}
def create(self, context):
+ print("Create")
m = bpy.data.meshes.new("Fence")
o = bpy.data.objects.new("Fence", m)
d = m.archipack_fence.add()
# make manipulators selectable
+ print("manipulable_selectable")
+
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
+ print("load_preset")
self.load_preset(d)
+ print("add_material")
+
self.add_material(o)
return o
def execute(self, context):
if context.mode == "OBJECT":
+ print("select_all")
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.location = bpy.context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ print("select_all")
+ o.location = context.scene.cursor_location
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
+ print("manipulate")
+
self.manipulate()
return {'FINISHED'}
else:
@@ -1663,7 +1669,7 @@ class ARCHIPACK_OT_fence_curve_update(Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def execute(self, context):
if context.mode == "OBJECT":
@@ -1689,7 +1695,7 @@ class ARCHIPACK_OT_fence_from_curve(ArchipackCreateTool, Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
o = None
@@ -1709,8 +1715,8 @@ class ARCHIPACK_OT_fence_from_curve(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
if o is not None:
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
# self.manipulate()
return {'FINISHED'}
else:
diff --git a/archipack/archipack_floor.py b/archipack/archipack_floor.py
index 25d4db2f..f53a78d7 100644
--- a/archipack/archipack_floor.py
+++ b/archipack/archipack_floor.py
@@ -225,7 +225,7 @@ class FloorGenerator(CutAblePolygon, CutAbleGenerator):
# rotate seg
seg.rotate(a)
# rotate delta from rotation center to segment start
- dp = rM * (seg.p0 - p0)
+ dp = rM @ (seg.p0 - p0)
seg.translate(dp)
def translate(self, idx_from, dp):
@@ -305,7 +305,7 @@ class FloorGenerator(CutAblePolygon, CutAbleGenerator):
use_dissolve_boundaries=False,
verts=bm.verts,
edges=bm.edges,
- delimit=1)
+ delimit={'MATERIAL'})
bm.verts.ensure_lookup_table()
@@ -333,11 +333,11 @@ class FloorGenerator(CutAblePolygon, CutAbleGenerator):
bmesh.ops.bevel(bm,
geom=geom,
offset=d.bevel_amount,
- offset_type=0,
+ offset_type='OFFSET',
segments=1, # d.bevel_res
profile=0.5,
vertex_only=False,
- clight_overlap=False,
+ clamp_overlap=False,
material=-1)
bm.to_mesh(o.data)
@@ -366,7 +366,7 @@ class FloorGenerator(CutAblePolygon, CutAbleGenerator):
use_dissolve_boundaries=False,
verts=bm.verts,
edges=bm.edges,
- delimit=1)
+ delimit={'MATERIAL'})
bm.verts.ensure_lookup_table()
@@ -925,7 +925,7 @@ class archipack_floor_part(PropertyGroup):
A single manipulable polyline like segment
polyline like segment line or arc based
"""
- type = EnumProperty(
+ type : EnumProperty(
items=(
('S_SEG', 'Straight', '', 0),
('C_SEG', 'Curved', '', 1),
@@ -933,19 +933,19 @@ class archipack_floor_part(PropertyGroup):
default='S_SEG',
update=update_type
)
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
default=2.0,
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.5,
default=0.7,
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -953,7 +953,7 @@ class archipack_floor_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- a0 = FloatProperty(
+ a0 : FloatProperty(
name="Start angle",
min=-2 * pi,
max=2 * pi,
@@ -961,21 +961,21 @@ class archipack_floor_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- offset = FloatProperty(
+ offset : FloatProperty(
name="Offset",
description="Side offset of segment",
default=0,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- manipulators = CollectionProperty(type=archipack_manipulator)
+ manipulators : CollectionProperty(type=archipack_manipulator)
def find_in_selection(self, context):
"""
find witch selected object this instance belongs to
provide support for "copy to selected"
"""
- selected = [o for o in context.selected_objects]
+ selected = context.selected_objects[:]
for o in selected:
props = archipack_floor.datablock(o)
if props:
@@ -1002,35 +1002,35 @@ class archipack_floor_part(PropertyGroup):
class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
- n_parts = IntProperty(
+ n_parts : IntProperty(
name="Parts",
min=1,
default=1, update=update_manipulators
)
- parts = CollectionProperty(type=archipack_floor_part)
- user_defined_path = StringProperty(
+ parts : CollectionProperty(type=archipack_floor_part)
+ user_defined_path : StringProperty(
name="User defined",
update=update_path
)
- user_defined_resolution = IntProperty(
+ user_defined_resolution : IntProperty(
name="Resolution",
min=1,
max=128,
default=12, update=update_path
)
- closed = BoolProperty(
+ closed : BoolProperty(
default=True,
name="Close",
options={'SKIP_SAVE'},
update=update_manipulators
)
# UI layout related
- parts_expand = BoolProperty(
+ parts_expand : BoolProperty(
options={'SKIP_SAVE'},
default=False
)
- pattern = EnumProperty(
+ pattern : EnumProperty(
name='Floor Pattern',
items=(("boards", "Boards", ""),
("square_parquet", "Square Parquet", ""),
@@ -1044,7 +1044,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
default="boards",
update=update
)
- spacing = FloatProperty(
+ spacing : FloatProperty(
name='Spacing',
description='The amount of space between boards or tiles in both directions',
unit='LENGTH', subtype='DISTANCE',
@@ -1053,7 +1053,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
precision=2,
update=update
)
- thickness = FloatProperty(
+ thickness : FloatProperty(
name='Thickness',
description='Thickness',
unit='LENGTH', subtype='DISTANCE',
@@ -1062,13 +1062,13 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
precision=2,
update=update
)
- vary_thickness = BoolProperty(
+ vary_thickness : BoolProperty(
name='Random Thickness',
description='Vary thickness',
default=False,
update=update
)
- thickness_variance = FloatProperty(
+ thickness_variance : FloatProperty(
name='Variance',
description='How much vary by',
min=0, max=100,
@@ -1078,7 +1078,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
update=update
)
- board_width = FloatProperty(
+ board_width : FloatProperty(
name='Width',
description='The width',
unit='LENGTH', subtype='DISTANCE',
@@ -1087,13 +1087,13 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
precision=2,
update=update
)
- vary_width = BoolProperty(
+ vary_width : BoolProperty(
name='Random Width',
description='Vary width',
default=False,
update=update
)
- width_variance = FloatProperty(
+ width_variance : FloatProperty(
name='Variance',
description='How much vary by',
subtype='PERCENTAGE',
@@ -1101,7 +1101,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
precision=2,
update=update
)
- width_spacing = FloatProperty(
+ width_spacing : FloatProperty(
name='Width Spacing',
description='The amount of space between boards in the width direction',
unit='LENGTH', subtype='DISTANCE',
@@ -1111,7 +1111,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
update=update
)
- board_length = FloatProperty(
+ board_length : FloatProperty(
name='Length',
description='The length of the boards',
unit='LENGTH', subtype='DISTANCE',
@@ -1120,7 +1120,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
default=2,
update=update
)
- short_board_length = FloatProperty(
+ short_board_length : FloatProperty(
name='Length',
description='The length of the boards',
unit='LENGTH', subtype='DISTANCE',
@@ -1129,27 +1129,27 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
default=2,
update=update
)
- vary_length = BoolProperty(
+ vary_length : BoolProperty(
name='Random Length',
description='Vary board length',
default=False,
update=update
)
- length_variance = FloatProperty(
+ length_variance : FloatProperty(
name='Variance',
description='How much board length can vary by',
subtype='PERCENTAGE',
min=1, max=100, default=50,
precision=2, update=update
)
- max_boards = IntProperty(
+ max_boards : IntProperty(
name='Max Boards',
description='Max number of boards in one row',
min=1,
default=20,
update=update
)
- length_spacing = FloatProperty(
+ length_spacing : FloatProperty(
name='Length Spacing',
description='The amount of space between boards in the length direction',
unit='LENGTH', subtype='DISTANCE',
@@ -1160,7 +1160,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
)
# parquet specific
- boards_in_group = IntProperty(
+ boards_in_group : IntProperty(
name='Boards in Group',
description='Number of boards in a group',
min=1, default=4,
@@ -1168,7 +1168,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
)
# tile specific
- tile_width = FloatProperty(
+ tile_width : FloatProperty(
name='Width',
description='Width of the tiles',
unit='LENGTH', subtype='DISTANCE',
@@ -1177,7 +1177,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
precision=2,
update=update
)
- tile_length = FloatProperty(
+ tile_length : FloatProperty(
name='Length',
description='Length of the tiles',
unit='LENGTH', subtype='DISTANCE',
@@ -1188,13 +1188,13 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
)
# grout
- add_grout = BoolProperty(
+ add_grout : BoolProperty(
name='Add Grout',
description='Add grout',
default=False,
update=update
)
- mortar_depth = FloatProperty(
+ mortar_depth : FloatProperty(
name='Depth',
description='The depth of the mortar from the surface of the tile',
unit='LENGTH', subtype='DISTANCE',
@@ -1206,19 +1206,19 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
)
# regular tile
- random_offset = BoolProperty(
+ random_offset : BoolProperty(
name='Random Offset',
description='Random amount of offset for each row of tiles',
update=update, default=False
)
- offset = FloatProperty(
+ offset : FloatProperty(
name='Offset',
description='How much to offset each row of tiles',
min=0, max=100, default=0,
precision=2,
update=update
)
- offset_variance = FloatProperty(
+ offset_variance : FloatProperty(
name='Variance',
description='How much to vary the offset each row of tiles',
min=0.001, max=100, default=50,
@@ -1227,13 +1227,13 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
)
# bevel
- bevel = BoolProperty(
+ bevel : BoolProperty(
name='Bevel',
update=update,
default=False,
description='Bevel upper faces'
)
- bevel_amount = FloatProperty(
+ bevel_amount : FloatProperty(
name='Bevel',
description='Bevel amount',
unit='LENGTH', subtype='DISTANCE',
@@ -1241,29 +1241,29 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
precision=2, step=0.05,
update=update
)
- solidify = BoolProperty(
+ solidify : BoolProperty(
name="Solidify",
default=True,
update=update
)
- vary_materials = BoolProperty(
+ vary_materials : BoolProperty(
name="Random Material",
default=True,
description="Vary Material indexes",
update=update)
- matid = IntProperty(
+ matid : IntProperty(
name="#variations",
min=1,
max=10,
default=7,
description="Material index maxi",
update=update)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
)
- z = FloatProperty(
+ z : FloatProperty(
name="dumb z",
description="Dumb z for manipulator placeholder",
default=0.01,
@@ -1324,18 +1324,18 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
# since this can lower points count by a resolution factor
# use normalized to handle non linear t
if resolution == 0:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
v = (p1.co - p0.co).normalized()
d1 = (p0.handle_right - p0.co).normalized()
d2 = (p1.co - p1.handle_left).normalized()
if d1 == v and d2 == v:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
- seg = interpolate_bezier(wM * p0.co,
- wM * p0.handle_right,
- wM * p1.handle_left,
- wM * p1.co,
+ seg = interpolate_bezier(wM @ p0.co,
+ wM @ p0.handle_right,
+ wM @ p1.handle_left,
+ wM @ p1.co,
resolution + 1)
for i in range(resolution):
pts.append(seg[i].to_3d())
@@ -1343,7 +1343,7 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
def from_spline(self, context, wM, resolution, spline):
pts = []
if spline.type == 'POLY':
- pts = [wM * p.co.to_3d() for p in spline.points]
+ pts = [wM @ p.co.to_3d() for p in spline.points]
if spline.use_cyclic_u:
pts.append(pts[0])
elif spline.type == 'BEZIER':
@@ -1358,18 +1358,13 @@ class archipack_floor(ArchipackObject, Manipulable, PropertyGroup):
self.interpolate_bezier(pts, wM, p0, p1, resolution)
pts.append(pts[0])
else:
- pts.append(wM * points[-1].co)
+ pts.append(wM @ points[-1].co)
- pt = wM.inverted() * pts[0]
+ pt = wM.inverted() @ pts[0]
# pretranslate
o = self.find_in_selection(context, self.auto_update)
- o.matrix_world = wM * Matrix([
- [1, 0, 0, pt.x],
- [0, 1, 0, pt.y],
- [0, 0, 1, pt.z],
- [0, 0, 0, 1]
- ])
+ o.matrix_world = wM @ Matrix.Translation(pt)
self.from_points(pts)
def from_points(self, pts):
@@ -1565,8 +1560,8 @@ def update_operation(self, context):
class archipack_floor_cutter_segment(ArchipackCutterPart, PropertyGroup):
- manipulators = CollectionProperty(type=archipack_manipulator)
- type = EnumProperty(
+ manipulators : CollectionProperty(type=archipack_manipulator)
+ type : EnumProperty(
name="Type",
items=(
('DEFAULT', 'Side', 'Side with rake', 0),
@@ -1599,7 +1594,7 @@ class archipack_floor_cutter_segment(ArchipackCutterPart, PropertyGroup):
class archipack_floor_cutter(ArchipackCutter, ArchipackObject, Manipulable, PropertyGroup):
- parts = CollectionProperty(type=archipack_floor_cutter_segment)
+ parts : CollectionProperty(type=archipack_floor_cutter_segment)
def update_points(self, context, o, pts, update_parent=False):
"""
@@ -1615,11 +1610,11 @@ class archipack_floor_cutter(ArchipackCutter, ArchipackObject, Manipulable, Prop
d = archipack_floor.datablock(o.parent)
if d is not None:
- o.parent.select = True
- context.scene.objects.active = o.parent
+ o.parent.select_set(state=True)
+ context.view_layer.objects.active = o.parent
d.update(context)
- o.parent.select = False
- context.scene.objects.active = o
+ o.parent.select_set(state=False)
+ context.view_layer.objects.active = o
# ------------------------------------------------------------------
@@ -1632,7 +1627,7 @@ class ARCHIPACK_PT_floor(Panel):
bl_label = "Flooring"
bl_space_type = "VIEW_3D"
bl_region_type = "UI"
- bl_category = "Archipack"
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1648,7 +1643,7 @@ class ARCHIPACK_PT_floor(Panel):
# retrieve datablock of your object
props = archipack_floor.datablock(o)
# manipulate
- layout.operator("archipack.floor_manipulate", icon="HAND")
+ layout.operator("archipack.floor_manipulate", icon="VIEW_PAN")
layout.separator()
box = layout.box()
row = box.row(align=True)
@@ -1658,10 +1653,10 @@ class ARCHIPACK_PT_floor(Panel):
text=bpy.types.ARCHIPACK_OT_floor_preset_menu.bl_label)
row.operator("archipack.floor_preset",
text="",
- icon='ZOOMIN')
+ icon='ADD')
row.operator("archipack.floor_preset",
text="",
- icon='ZOOMOUT').remove_active = True
+ icon='REMOVE').remove_active = True
box = layout.box()
box.operator('archipack.floor_cutter').parent = o.name
@@ -1759,7 +1754,7 @@ class ARCHIPACK_PT_floor_cutter(Panel):
bl_label = "Floor Cutter"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1772,7 +1767,7 @@ class ARCHIPACK_PT_floor_cutter(Panel):
layout = self.layout
scene = context.scene
box = layout.box()
- box.operator('archipack.floor_cutter_manipulate', icon='HAND')
+ box.operator('archipack.floor_cutter_manipulate', icon='VIEW_PAN')
box.prop(prop, 'operation', text="")
box = layout.box()
box.label(text="From curve")
@@ -1824,9 +1819,9 @@ class ARCHIPACK_OT_floor(ArchipackCreateTool, Operator):
p.a0 = angle_90
p.length = x
d.n_parts = 4
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.load_preset(d)
self.add_material(o)
return o
@@ -1837,8 +1832,8 @@ class ARCHIPACK_OT_floor(ArchipackCreateTool, Operator):
o = self.create(context)
o.location = context.scene.cursor_location
# activate manipulators at creation time
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
@@ -1864,7 +1859,7 @@ class ARCHIPACK_OT_floor_from_curve(ArchipackCreateTool, Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
curve = context.active_object
@@ -1903,7 +1898,7 @@ class ARCHIPACK_OT_floor_from_wall(ArchipackCreateTool, Operator):
wall = context.active_object
wd = wall.data.archipack_wall2[0]
bpy.ops.archipack.floor(auto_manipulate=False, filepath=self.filepath)
- o = context.scene.objects.active
+ o = context.view_layer.objects.active
d = archipack_floor.datablock(o)
d.auto_update = False
d.closed = True
@@ -1931,8 +1926,8 @@ class ARCHIPACK_OT_floor_from_wall(ArchipackCreateTool, Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
if self.auto_manipulate:
bpy.ops.archipack.floor_manipulate('INVOKE_DEFAULT')
return {'FINISHED'}
@@ -1948,7 +1943,7 @@ class ARCHIPACK_OT_floor_cutter(ArchipackCreateTool, Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- parent = StringProperty("")
+ parent : StringProperty("")
def create(self, context):
m = bpy.data.meshes.new("Floor Cutter")
@@ -1963,7 +1958,7 @@ class ARCHIPACK_OT_floor_cutter(ArchipackCreateTool, Operator):
x1, y1, z = bbox[6]
x = 0.2 * (x1 - x0)
y = 0.2 * (y1 - y0)
- o.matrix_world = parent.matrix_world * Matrix([
+ o.matrix_world = parent.matrix_world @ Matrix([
[1, 0, 0, -3 * x],
[0, 1, 0, 0],
[0, 0, 1, 0],
@@ -1986,9 +1981,9 @@ class ARCHIPACK_OT_floor_cutter(ArchipackCreateTool, Operator):
o.location = context.scene.cursor_location
# make manipulators selectable
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
# self.add_material(o)
self.load_preset(d)
update_operation(d, context)
@@ -2001,8 +1996,8 @@ class ARCHIPACK_OT_floor_cutter(ArchipackCreateTool, Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
diff --git a/archipack/archipack_gl.py b/archipack/archipack_gl.py
index 8c475617..578098f9 100644
--- a/archipack/archipack_gl.py
+++ b/archipack/archipack_gl.py
@@ -24,10 +24,12 @@
# Author: Stephen Leger (s-leger)
#
# ----------------------------------------------------------
-
import bgl
import blf
+import gpu
+from gpu_extras.batch import batch_for_shader
import bpy
+import numpy as np
from math import sin, cos, atan2, pi
from mathutils import Vector, Matrix
from bpy_extras import view3d_utils, object_utils
@@ -44,6 +46,7 @@ class DefaultColorScheme:
default to this when not found in addon prefs
Colors are FloatVectorProperty of size 4 and type COLOR_GAMMA
"""
+ text_size = 14
feedback_size_main = 16
feedback_size_title = 14
feedback_size_shortcut = 11
@@ -52,6 +55,167 @@ class DefaultColorScheme:
feedback_colour_shortcut = (0.51, 0.51, 0.51, 1.0)
feedback_shortcut_area = (0, 0.4, 0.6, 0.2)
feedback_title_area = (0, 0.4, 0.6, 0.5)
+ handle_colour_normal = (1.0, 1.0, 1.0, 1.0)
+ handle_colour_hover = (1.0, 1.0, 0.0, 1.0)
+ handle_colour_active = (1.0, 0.0, 0.0, 1.0)
+ handle_colour_selected = (0.0, 0.0, 0.7, 1.0)
+ handle_colour_inactive = (0.3, 0.3, 0.3, 1.0)
+
+
+def get_prefs(context):
+ global __name__
+ try:
+ addon_name = __name__.split('.')[0]
+ prefs = context.user_preferences.addons[addon_name].preferences
+ except:
+ prefs = DefaultColorScheme
+ pass
+ return prefs
+
+
+g_poly = None
+g_image = None
+g_line = None
+
+
+line_vertSrc = '''
+uniform mat4 ModelViewProjectionMatrix;
+
+in vec2 pos;
+
+void main()
+{
+ gl_Position = ModelViewProjectionMatrix * vec4(pos, 0.0, 1.0);
+}
+
+'''
+
+line_fragSrc = '''
+uniform vec4 color;
+
+out vec4 fragColor;
+
+void main()
+{
+ fragColor = color;
+}
+'''
+
+"""
+# TESTS
+_format = gpu.types.GPUVertFormat()
+_pos_id = _format.attr_add(
+ id="pos",
+ comp_type="F32",
+ len=2,
+ fetch_mode="FLOAT")
+coords = [(0,0), (200,100)]
+vbo = gpu.types.GPUVertBuf(len=len(coords), format=_format)
+"""
+
+
+class GPU_Line:
+ def __init__(self):
+ # never call this in -b mode
+ if bpy.app.background:
+ return
+ self._format = gpu.types.GPUVertFormat()
+ self._pos_id = self._format.attr_add(
+ id="pos",
+ comp_type="F32",
+ len=2,
+ fetch_mode="FLOAT")
+ self.shader = gpu.types.GPUShader(line_vertSrc, line_fragSrc)
+ self.unif_color = self.shader.uniform_from_name("color")
+ self.color = np.array([0.0, 0.0, 0.0, 1.0], 'f')
+
+ def batch_line_strip_create(self, coords):
+ vbo = gpu.types.GPUVertBuf(len=len(coords), format=self._format)
+ vbo.attr_fill(id=self._pos_id, data=coords)
+ batch_lines = gpu.types.GPUBatch(type="LINE_STRIP", buf=vbo)
+ batch_lines.program_set(self.shader)
+ return batch_lines
+
+ def draw(self, color, list_verts_co):
+ if list_verts_co:
+ batch = self.batch_line_strip_create(list_verts_co)
+ self.color[0:4] = color[0:4]
+ self.shader.uniform_vector_float(self.unif_color, self.color, 4)
+ batch.draw()
+ del batch
+
+
+class GPU_Poly:
+
+ def __init__(self):
+ if bpy.app.background:
+ return
+ self._format = gpu.types.GPUVertFormat()
+ self._pos_id = self._format.attr_add(
+ id="pos",
+ comp_type="F32",
+ len=2,
+ fetch_mode="FLOAT")
+ self.shader = gpu.types.GPUShader(line_vertSrc, line_fragSrc)
+ self.unif_color = self.shader.uniform_from_name("color")
+ self.color = np.array([0.0, 0.0, 0.0, 0.5], 'f')
+
+ def batch_create(self, coords):
+ vbo = gpu.types.GPUVertBuf(len=len(coords), format=self._format)
+ vbo.attr_fill(id=self._pos_id, data=coords)
+ batch = gpu.types.GPUBatch(type="TRI_FAN", buf=vbo)
+ # batch.program_set(self.shader)
+ # batch = batch_for_shader(self.shader, 'TRI_FAN', {"position": coords})
+ return batch
+
+ def draw(self, color, list_verts_co):
+ if list_verts_co:
+ self.shader.bind()
+ batch = self.batch_create(list_verts_co)
+ self.color[0:4] = color[0:4]
+ self.shader.uniform_vector_float(self.unif_color, self.color, 4)
+ batch.draw(self.shader)
+
+
+class GPU_Image:
+ uvs = [(0, 0), (1, 0), (0, 1), (1, 1)]
+ indices = [(0, 1, 2), (2, 1, 3)]
+
+ def __init__(self):
+ if bpy.app.background:
+ return
+ self._format = gpu.types.GPUVertFormat()
+ self._pos_id = self._format.attr_add(
+ id="pos",
+ comp_type="F32",
+ len=2,
+ fetch_mode="FLOAT")
+ self.shader = gpu.shader.from_builtin('2D_IMAGE')
+
+ def batch_create(self, coords):
+ batch = batch_for_shader(self.shader, 'TRIS',
+ {"pos": coords,
+ "texCoord": self.uvs},
+ indices=self.indices)
+ return batch
+
+ def draw(self, texture_id, list_verts_co):
+ if list_verts_co:
+ batch = self.batch_create(list_verts_co)
+
+ # in case someone disabled it before
+ bgl.glEnable(bgl.GL_TEXTURE_2D)
+
+ # bind texture to image unit 0
+ bgl.glActiveTexture(bgl.GL_TEXTURE0)
+ bgl.glBindTexture(bgl.GL_TEXTURE_2D, texture_id)
+
+ self.shader.bind()
+ # tell shader to use the image that is bound to image unit 0
+ self.shader.uniform_int("image", 0)
+ batch.draw(self.shader)
+
+ bgl.glDisable(bgl.GL_TEXTURE_2D)
class Gl():
@@ -61,9 +225,22 @@ class Gl():
3 to convert pos from 3d
2 to keep pos as 2d absolute screen position
"""
+
def __init__(self,
- d=3,
- colour=(0.0, 0.0, 0.0, 1.0)):
+ d=3,
+ colour=(0.0, 0.0, 0.0, 1.0)):
+
+ global g_poly, g_image, g_line
+
+ if g_poly is None:
+ g_poly = GPU_Poly()
+
+ if g_image is None:
+ g_image = GPU_Image()
+
+ if g_line is None:
+ g_line = GPU_Line()
+
# nth dimensions of input coords 3=word coords 2=pixel screen coords
self.d = d
self.pos_2d = Vector((0, 0))
@@ -77,13 +254,13 @@ class Gl():
""" coord given in local input coordsys
"""
if self.d == 2:
- return coord
+ return Vector(coord)
if render:
return self.get_render_location(context, coord)
region = context.region
rv3d = context.region_data
loc = view3d_utils.location_3d_to_region_2d(region, rv3d, coord, self.pos_2d)
- return loc
+ return Vector(loc)
def get_render_location(self, context, coord):
scene = context.scene
@@ -92,42 +269,32 @@ class Gl():
render_scale = scene.render.resolution_percentage / 100
render_size = (int(scene.render.resolution_x * render_scale),
int(scene.render.resolution_y * render_scale))
- return [round(co_2d.x * render_size[0]), round(co_2d.y * render_size[1])]
-
- def _end(self):
-
- # print("_end")
- bgl.glEnd()
- bgl.glPopAttrib()
- bgl.glLineWidth(1)
- bgl.glDisable(bgl.GL_BLEND)
- bgl.glColor4f(0.0, 0.0, 0.0, 1.0)
- # print("_end %s" % (type(self).__name__))
+ return Vector(round(co_2d.x * render_size[0]), round(co_2d.y * render_size[1]))
class GlText(Gl):
def __init__(self,
- d=3,
- label="",
- value=None,
- precision=2,
- unit_mode='AUTO',
- unit_type='SIZE',
- dimension=1,
- angle=0,
- font_size=12,
- colour=(1, 1, 1, 1),
- z_axis=Vector((0, 0, 1))):
+ d=3,
+ label="",
+ value=None,
+ precision=4,
+ unit_mode='AUTO',
+ unit_type='SIZE',
+ dimension=1,
+ angle=0,
+ font_size=None,
+ colour=(1, 1, 1, 1),
+ z_axis=Vector((0, 0, 1))):
"""
d: [2|3] coords type: 2 for coords in screen pixels, 3 for 3d world location
label : string label
value : float value (will add unit according following settings)
precision : integer rounding for values
dimension : [1 - 3] nth dimension of unit (single, square, cubic)
- unit_mode : ['AUTO','METER','CENTIMETER','MILIMETER','FEET','INCH','RADIANS','DEGREE']
+ unit_mode : ['ADAPTIVE','METER','CENTIMETER','MILIMETER','FEET','INCH','RADIANS','DEGREE']
unit type to use to postfix values
- auto use scene units setup
+ ADAPTIVE use scene units setup
unit_type : ['SIZE','ANGLE']
unit type to add to value
angle : angle to rotate text
@@ -142,13 +309,17 @@ class GlText(Gl):
self.dimension = dimension
self.unit_type = unit_type
self.unit_mode = unit_mode
-
- self.font_size = font_size
+ if font_size is None:
+ prefs = get_prefs(bpy.context)
+ self.font_size = prefs.text_size
+ else:
+ self.font_size = font_size
self.angle = angle
Gl.__init__(self, d)
self.colour_inactive = colour
# store text with units
self._text = ""
+ self.cbuff = bgl.Buffer(bgl.GL_FLOAT, 4)
def text_size(self, context):
"""
@@ -177,20 +348,25 @@ class GlText(Gl):
def add_units(self, context):
if self.value is None:
return ""
+ system = context.scene.unit_settings.system
if self.unit_type == 'ANGLE':
scale = 1
+ mode = 'ADAPTIVE'
else:
scale = context.scene.unit_settings.scale_length
+ mode = self.unit_mode
+ if mode == 'AUTO':
+ mode = context.scene.unit_settings.length_unit.upper()
val = self.value * scale
- mode = self.unit_mode
- if mode == 'AUTO':
+
+ if mode == 'ADAPTIVE':
if self.unit_type == 'ANGLE':
mode = context.scene.unit_settings.system_rotation
else:
- if context.scene.unit_settings.system == "IMPERIAL":
+ if system == "IMPERIAL":
if round(val * (3.2808399 ** self.dimension), 2) >= 1.0:
- mode = 'FEET'
+ mode = 'FOOT'
else:
mode = 'INCH'
elif context.scene.unit_settings.system == "METRIC":
@@ -201,7 +377,10 @@ class GlText(Gl):
mode = 'CENTIMETER'
else:
mode = 'MILIMETER'
+
+ # TODO: support for separate units (through 2.8 api)
# convert values
+ unit = ""
if mode == 'METER':
unit = "m"
elif mode == 'CENTIMETER':
@@ -210,26 +389,38 @@ class GlText(Gl):
elif mode == 'MILIMETER':
val *= (1000 ** self.dimension)
unit = 'mm'
+ elif mode in {'FOOT', 'FEET'}:
+ val *= (3.2808399 ** self.dimension)
+ unit = "ft"
elif mode == 'INCH':
val *= (39.3700787 ** self.dimension)
unit = "in"
- elif mode == 'FEET':
- val *= (3.2808399 ** self.dimension)
- unit = "ft"
elif mode == 'RADIANS':
unit = ""
elif mode == 'DEGREES':
val = self.value / pi * 180
unit = "°"
- else:
- unit = ""
- if self.dimension == 2:
- unit += "\u00b2" # Superscript two
- elif self.dimension == 3:
- unit += "\u00b3" # Superscript three
-
- fmt = "%1." + str(self.precision) + "f " + unit
- return fmt % val
+ if system == 'IMPERIAL':
+ if self.dimension == 2:
+ unit = "sq " + unit
+ elif self.dimension == 3:
+ unit = "cu " + unit
+ elif system == 'METRIC':
+ if self.dimension == 2:
+ unit += "\u00b2" # Superscript two
+ elif self.dimension == 3:
+ unit += "\u00b3" # Superscript three
+
+ fmt = "%1." + str(self.precision) + "f"
+ # remove trailing zeros
+ res = fmt % val
+ while res[-1] == '0':
+ res = res[:-1]
+
+ if res[-1] == ".":
+ res = res + '0'
+
+ return "{} {}".format(res, unit)
def set_pos(self, context, value, pos_3d, direction, angle=0, normal=Vector((0, 0, 1))):
self.up_axis = direction.normalized()
@@ -243,66 +434,68 @@ class GlText(Gl):
# print("draw_text %s %s" % (self.text, type(self).__name__))
self.render = render
- x, y = self.position_2d_from_coord(context, self.pts[0], render)
+ p = self.position_2d_from_coord(context, self.pts[0], render)
+
# dirty fast assignment
dpi, font_id = context.user_preferences.system.dpi, 0
- bgl.glColor4f(*self.colour)
+
+ # self.cbuff[0:4] = self.colour
+
+ # bgl.glEnableClientState(bgl.GL_COLOR_ARRAY)
+ # bgl.glColorPointer(4, bgl.GL_FLOAT, 0, self.cbuff)
+ blf.color(0, *self.colour)
if self.angle != 0:
blf.enable(font_id, blf.ROTATION)
blf.rotation(font_id, self.angle)
blf.size(font_id, self.font_size, dpi)
- blf.position(font_id, x, y, 0)
+ blf.position(font_id, p.x, p.y, 0)
blf.draw(font_id, self.text)
if self.angle != 0:
blf.disable(font_id, blf.ROTATION)
+ # bgl.glDisableClientState(bgl.GL_COLOR_ARRAY)
+
class GlBaseLine(Gl):
def __init__(self,
- d=3,
- width=1,
- style=bgl.GL_LINE,
- closed=False):
+ d=3,
+ width=1,
+ style=bgl.GL_LINE,
+ closed=False,
+ n_pts=2):
Gl.__init__(self, d)
# default line width
self.width = width
# default line style
self.style = style
# allow closed lines
- self.closed = False
+ self.closed = closed
+
+ self.n_pts = n_pts
def draw(self, context, render=False):
"""
render flag when rendering
"""
-
- # print("draw_line %s" % (type(self).__name__))
- bgl.glPushAttrib(bgl.GL_ENABLE_BIT)
- if self.style == bgl.GL_LINE_STIPPLE:
- bgl.glLineStipple(1, 0x9999)
- bgl.glEnable(self.style)
+ self.render = render
bgl.glEnable(bgl.GL_BLEND)
- if render:
- # enable anti-alias on lines
- bgl.glEnable(bgl.GL_LINE_SMOOTH)
- bgl.glColor4f(*self.colour)
bgl.glLineWidth(self.width)
+ list_verts_co = [
+ tuple(self.position_2d_from_coord(context, pt, render)[0:2])
+ for i, pt in enumerate(self.pts)]
if self.closed:
- bgl.glBegin(bgl.GL_LINE_LOOP)
- else:
- bgl.glBegin(bgl.GL_LINE_STRIP)
-
- for pt in self.pts:
- x, y = self.position_2d_from_coord(context, pt, render)
- bgl.glVertex2f(x, y)
- self._end()
+ list_verts_co.append(list_verts_co[0])
+ g_line.draw(self.colour, list_verts_co)
+ bgl.glLineWidth(1.0)
+ bgl.glDisable(bgl.GL_BLEND)
class GlLine(GlBaseLine):
"""
2d/3d Line
"""
+
def __init__(self, d=3, p=None, v=None, p0=None, p1=None, z_axis=None):
"""
d=3 use 3d coords, d=2 use 2d pixels coords
@@ -322,13 +515,13 @@ class GlLine(GlBaseLine):
self.p = Vector(p0)
self.v = Vector(p1) - self.p
else:
- self.p = Vector((0, 0, 0))
- self.v = Vector((0, 0, 0))
+ self.p = Vector()
+ self.v = Vector()
if z_axis is not None:
self.z_axis = z_axis
else:
self.z_axis = Vector((0, 0, 1))
- GlBaseLine.__init__(self, d)
+ GlBaseLine.__init__(self, d, n_pts=2)
@property
def p0(self):
@@ -391,7 +584,7 @@ class GlLine(GlBaseLine):
def sized_normal(self, t, size):
"""
GlLine perpendicular on plane defined by z_axis and of given size
- positioned at t in current line
+ positionned at t in current line
lie on the right side
p1
|--x
@@ -425,7 +618,7 @@ class GlLine(GlBaseLine):
v2d = self.v.to_2d()
dl = v2d.length
d = (self.v.x * dp.y - self.v.y * dp.x) / dl
- t = (v2d * dp) / (dl * dl)
+ t = v2d.dot(dp) / (dl * dl)
return t > 0 and t < 1, d, t
@property
@@ -436,10 +629,10 @@ class GlLine(GlBaseLine):
class GlCircle(GlBaseLine):
def __init__(self,
- d=3,
- radius=0,
- center=Vector((0, 0, 0)),
- z_axis=Vector((0, 0, 1))):
+ d=3,
+ radius=0,
+ center=Vector((0, 0, 0)),
+ z_axis=Vector((0, 0, 1))):
self.r = radius
self.c = center
@@ -460,18 +653,19 @@ class GlCircle(GlBaseLine):
self.z_axis = z
self.a0 = 0
self.da = 2 * pi
- GlBaseLine.__init__(self, d)
+ GlBaseLine.__init__(self, d, n_pts=60)
def lerp(self, t):
"""
Linear interpolation
"""
a = self.a0 + t * self.da
- return self.c + self.rM * Vector((self.r * cos(a), self.r * sin(a), 0))
+ return self.c + self.rM @ Vector((self.r * cos(a), self.r * sin(a), 0))
@property
def pts(self):
n_pts = max(1, int(round(abs(self.da) / pi * 30, 0)))
+ self.n_pts = n_pts
t_step = 1 / n_pts
return [self.lerp(i * t_step) for i in range(n_pts + 1)]
@@ -479,12 +673,12 @@ class GlCircle(GlBaseLine):
class GlArc(GlCircle):
def __init__(self,
- d=3,
- radius=0,
- center=Vector((0, 0, 0)),
- z_axis=Vector((0, 0, 1)),
- a0=0,
- da=0):
+ d=3,
+ radius=0,
+ center=Vector((0, 0, 0)),
+ z_axis=Vector((0, 0, 1)),
+ a0=0,
+ da=0):
"""
a0 and da arguments are in radians
a0 = 0 on the x+ axis side
@@ -526,8 +720,8 @@ class GlArc(GlCircle):
ca = cos(a)
sa = sin(a)
n = GlLine(d=self.d, z_axis=self.z_axis)
- n.p = self.c + self.rM * Vector((self.r * ca, self.r * sa, 0))
- n.v = self.rM * Vector((length * sa, -length * ca, 0))
+ n.p = self.c + self.rM @ Vector((self.r * ca, self.r * sa, 0))
+ n.v = self.rM @ Vector((length * sa, -length * ca, 0))
if self.da > 0:
n.v = -n.v
return n
@@ -541,22 +735,23 @@ class GlArc(GlCircle):
else:
radius = self.r - offset
return GlArc(d=self.d,
- radius=radius,
- center=self.c,
- a0=self.a0,
- da=self.da,
- z_axis=self.z_axis)
+ radius=radius,
+ center=self.c,
+ a0=self.a0,
+ da=self.da,
+ z_axis=self.z_axis)
class GlPolygon(Gl):
def __init__(self,
- colour=(0.0, 0.0, 0.0, 1.0),
- d=3):
-
+ colour=(0.3, 0.3, 0.3, 1.0),
+ d=3, n_pts=60):
self.pts_3d = []
Gl.__init__(self, d, colour)
+ self.n_pts = min(n_pts, 60)
+
def set_pos(self, pts_3d):
self.pts_3d = pts_3d
@@ -568,52 +763,53 @@ class GlPolygon(Gl):
"""
render flag when rendering
"""
+ # return
- # print("draw_polygon")
self.render = render
- bgl.glPushAttrib(bgl.GL_ENABLE_BIT)
- bgl.glEnable(bgl.GL_BLEND)
- if render:
- # enable anti-alias on polygons
- bgl.glEnable(bgl.GL_POLYGON_SMOOTH)
- bgl.glColor4f(*self.colour)
- bgl.glBegin(bgl.GL_POLYGON)
+ if self.n_pts == 0:
+ return
+
+ pts = self.pts
- for pt in self.pts:
- x, y = self.position_2d_from_coord(context, pt, render)
- bgl.glVertex2f(x, y)
- self._end()
+ g_vertices = [
+ tuple(self.position_2d_from_coord(context, pt, render)[0:2])
+ for i, pt in enumerate(pts)]
+ bgl.glEnable(bgl.GL_BLEND)
+ g_poly.draw(self.colour, g_vertices)
+ bgl.glDisable(bgl.GL_BLEND)
class GlRect(GlPolygon):
def __init__(self,
- colour=(0.0, 0.0, 0.0, 1.0),
- d=2):
- GlPolygon.__init__(self, colour, d)
+ colour=(0.0, 0.0, 0.0, 1.0),
+ d=2):
+ GlPolygon.__init__(self, colour, d, n_pts=4)
- def draw(self, context, render=False):
+ @property
+ def pts(self):
+ return self.pts_2d
- self.render = render
- bgl.glPushAttrib(bgl.GL_ENABLE_BIT)
- bgl.glEnable(bgl.GL_BLEND)
- if render:
- # enable anti-alias on polygons
- bgl.glEnable(bgl.GL_POLYGON_SMOOTH)
- bgl.glColor4f(*self.colour)
- p0 = self.pts[0]
- p1 = self.pts[1]
- bgl.glRectf(p0.x, p0.y, p1.x, p1.y)
- self._end()
+ def draw(self, context, render=False):
+ pts = [
+ self.position_2d_from_coord(context, pt, render)
+ for pt in self.pts_3d
+ ]
+ x0, y0 = pts[0]
+ x1, y1 = pts[1]
+ self.pts_2d = [Vector((x, y)) for x, y in [(x0, y0), (x0, y1), (x1, y1), (x1, y0)]]
+ GlPolygon.draw(self, context, render)
class GlImage(Gl):
def __init__(self,
- d=2,
- image=None):
+ d=2,
+ image=None):
+ # GImage bindcode[0]
self.image = image
self.colour_inactive = (1, 1, 1, 1)
Gl.__init__(self, d)
self.pts_2d = [Vector((0, 0)), Vector((10, 10))]
+ self.n_pts = 4
def set_pos(self, pts):
self.pts_2d = pts
@@ -625,38 +821,17 @@ class GlImage(Gl):
def draw(self, context, render=False):
if self.image is None:
return
- bgl.glPushAttrib(bgl.GL_ENABLE_BIT)
+
p0 = self.pts[0]
p1 = self.pts[1]
- bgl.glEnable(bgl.GL_BLEND)
- bgl.glColor4f(*self.colour)
- bgl.glRectf(p0.x, p0.y, p1.x, p1.y)
- self.image.gl_load()
- bgl.glEnable(bgl.GL_BLEND)
- bgl.glBindTexture(bgl.GL_TEXTURE_2D, self.image.bindcode[0])
- bgl.glTexParameteri(bgl.GL_TEXTURE_2D, bgl.GL_TEXTURE_MIN_FILTER, bgl.GL_NEAREST)
- bgl.glTexParameteri(bgl.GL_TEXTURE_2D, bgl.GL_TEXTURE_MAG_FILTER, bgl.GL_NEAREST)
- bgl.glEnable(bgl.GL_TEXTURE_2D)
- bgl.glBlendFunc(bgl.GL_SRC_ALPHA, bgl.GL_ONE_MINUS_SRC_ALPHA)
- # bgl.glColor4f(1, 1, 1, 1)
- bgl.glBegin(bgl.GL_QUADS)
- bgl.glTexCoord2d(0, 0)
- bgl.glVertex2d(p0.x, p0.y)
- bgl.glTexCoord2d(0, 1)
- bgl.glVertex2d(p0.x, p1.y)
- bgl.glTexCoord2d(1, 1)
- bgl.glVertex2d(p1.x, p1.y)
- bgl.glTexCoord2d(1, 0)
- bgl.glVertex2d(p1.x, p0.y)
- bgl.glEnd()
- self.image.gl_free()
- bgl.glDisable(bgl.GL_TEXTURE_2D)
+ coords = [(p0.x, p0.y), (p1.x, p0.y), (p0.x, p1.y), (p1.x, p1.y)]
+ g_image.draw(self.image.bindcode, coords)
class GlPolyline(GlBaseLine):
- def __init__(self, colour, d=3):
+ def __init__(self, colour, d=3, n_pts=60):
self.pts_3d = []
- GlBaseLine.__init__(self, d)
+ GlBaseLine.__init__(self, d, n_pts=n_pts)
self.colour_inactive = colour
def set_pos(self, pts_3d):
@@ -670,17 +845,25 @@ class GlPolyline(GlBaseLine):
class GlHandle(GlPolygon):
- def __init__(self, sensor_size, size, draggable=False, selectable=False, d=3):
+ def __init__(self, sensor_size, size, draggable=False, selectable=False, d=3, n_pts=4):
"""
sensor_size : 2d size in pixels of sensor area
size : 3d size of handle
"""
- GlPolygon.__init__(self, d=d)
- self.colour_active = (1.0, 0.0, 0.0, 1.0)
- self.colour_hover = (1.0, 1.0, 0.0, 1.0)
- self.colour_normal = (1.0, 1.0, 1.0, 1.0)
- self.colour_selected = (0.0, 0.0, 0.7, 1.0)
+ GlPolygon.__init__(self, d=d, n_pts=n_pts)
+ prefs = get_prefs(bpy.context)
+ self.colour_active = prefs.handle_colour_active
+ self.colour_hover = prefs.handle_colour_hover
+ self.colour_normal = prefs.handle_colour_normal
+ self.colour_selected = prefs.handle_colour_selected
+ self.colour_inactive = prefs.handle_colour_inactive
+ # variable symbol size in world coords
self.size = size
+ # constant symbol size in pixels
+ self.symbol_size = sensor_size
+ # scale factor for constant symbol pixel size
+ self.scale = 1
+ # sensor size in pixels
self.sensor_width = sensor_size
self.sensor_height = sensor_size
self.pos_3d = Vector((0, 0, 0))
@@ -692,11 +875,38 @@ class GlHandle(GlPolygon):
self.selectable = selectable
self.selected = False
+ def scale_factor(self, context, pts):
+ """
+ Compute screen scale factor for symbol
+ given 2 points in symbol direction (eg start and end of arrow)
+ """
+ prefs = get_prefs(context)
+ if not prefs.constant_handle_size:
+ return 1
+
+ p2d = []
+ for pt in pts:
+ p2d.append(self.position_2d_from_coord(context, pt))
+ sx = [p.x for p in p2d]
+ sy = [p.y for p in p2d]
+ x = max(sx) - min(sx)
+ y = max(sy) - min(sy)
+ s = max(x, y)
+ if s > 0:
+ fac = self.symbol_size / s
+ else:
+ fac = 1
+ return fac
+
def set_pos(self, context, pos_3d, direction, normal=Vector((0, 0, 1))):
self.up_axis = direction.normalized()
self.c_axis = self.up_axis.cross(normal)
self.pos_3d = pos_3d
self.pos_2d = self.position_2d_from_coord(context, self.sensor_center)
+ x = self.up_axis * 0.5 * self.size
+ y = self.c_axis * 0.5 * self.size
+ pts = [self.sensor_center + v for v in [-x, x, -y, y]]
+ self.scale = self.scale_factor(context, pts)
def check_hover(self, pos_2d):
if self.draggable:
@@ -737,7 +947,7 @@ class GlHandle(GlPolygon):
class SquareHandle(GlHandle):
def __init__(self, sensor_size, size, draggable=False, selectable=False):
- GlHandle.__init__(self, sensor_size, size, draggable, selectable)
+ GlHandle.__init__(self, sensor_size, size, draggable, selectable, n_pts=4)
@property
def pts(self):
@@ -747,15 +957,15 @@ class SquareHandle(GlHandle):
scale = 1
else:
scale = 0.5
- x = n * self.size * scale
- y = c * self.size * scale
+ x = n * self.scale * self.size * scale
+ y = c * self.scale * self.size * scale
return [self.pos_3d - x - y, self.pos_3d + x - y, self.pos_3d + x + y, self.pos_3d - x + y]
class TriHandle(GlHandle):
def __init__(self, sensor_size, size, draggable=False, selectable=False):
- GlHandle.__init__(self, sensor_size, size, draggable, selectable)
+ GlHandle.__init__(self, sensor_size, size, draggable, selectable, n_pts=3)
@property
def pts(self):
@@ -767,11 +977,110 @@ class TriHandle(GlHandle):
scale = 1
# else:
# scale = 0.5
- x = n * self.size * 4 * scale
- y = c * self.size * scale
+ x = n * self.scale * self.size * 4 * scale
+ y = c * self.scale * self.size * scale
return [self.pos_3d - x + y, self.pos_3d - x - y, self.pos_3d]
+class CruxHandle(GlHandle):
+
+ def __init__(self, sensor_size, size, draggable=True, selectable=False):
+ GlHandle.__init__(self, sensor_size, size, draggable, selectable, n_pts=0)
+ self.branch_0 = GlPolygon((1, 1, 1, 1), d=3, n_pts=4)
+ self.branch_1 = GlPolygon((1, 1, 1, 1), d=3, n_pts=4)
+
+ def set_pos(self, context, pos_3d, direction, normal=Vector((0, 0, 1))):
+ self.pos_3d = pos_3d
+ self.pos_2d = self.position_2d_from_coord(context, self.sensor_center)
+ o = self.pos_3d
+ d = 0.5 * self.size
+ x = direction.normalized()
+ y = x.cross(normal)
+
+ sx = x * 0.5 * self.size
+ sy = y * 0.5 * self.size
+ pts = [o + v for v in [-sx, sx, -sy, sy]]
+ self.scale = self.scale_factor(context, pts)
+
+ c = self.scale * d / 1.4242
+ w = self.scale * self.size
+ s = w - c
+
+ xs = x * s
+ xw = x * w
+ ys = y * s
+ yw = y * w
+ p0 = o + xs + yw
+ p1 = o + xw + ys
+ p2 = o - xs - yw
+ p3 = o - xw - ys
+ p4 = o - xs + yw
+ p5 = o + xw - ys
+ p6 = o + xs - yw
+ p7 = o - xw + ys
+
+ self.branch_0.set_pos([p0, p1, p2, p3])
+ self.branch_1.set_pos([p4, p5, p6, p7])
+
+ @property
+ def pts(self):
+ return [self.pos_3d]
+
+ def draw(self, context, render=False):
+ self.render = render
+ self.branch_0.colour_inactive = self.colour
+ self.branch_1.colour_inactive = self.colour
+ self.branch_0.draw(context)
+ self.branch_1.draw(context)
+
+
+class PlusHandle(GlHandle):
+
+ def __init__(self, sensor_size, size, draggable=True, selectable=False):
+ GlHandle.__init__(self, sensor_size, size, draggable, selectable, n_pts=0)
+ self.branch_0 = GlPolygon((1, 1, 1, 1), d=3, n_pts=4)
+ self.branch_1 = GlPolygon((1, 1, 1, 1), d=3, n_pts=4)
+
+ def set_pos(self, context, pos_3d, direction, normal=Vector((0, 0, 1))):
+ self.pos_3d = pos_3d
+ self.pos_2d = self.position_2d_from_coord(context, self.sensor_center)
+ o = self.pos_3d
+ x = direction.normalized()
+ y = x.cross(normal)
+ sx = x * 0.5 * self.size
+ sy = y * 0.5 * self.size
+ pts = [o + v for v in [-sx, sx, -sy, sy]]
+ self.scale = self.scale_factor(context, pts)
+ w = self.scale * self.size
+ s = self.scale * 0.25 * w
+
+ xs = x * s
+ xw = x * w
+ ys = y * s
+ yw = y * w
+ p0 = o - xw + ys
+ p1 = o + xw + ys
+ p2 = o + xw - ys
+ p3 = o - xw - ys
+ p4 = o - xs + yw
+ p5 = o + xs + yw
+ p6 = o + xs - yw
+ p7 = o - xs - yw
+ self.branch_0.set_pos([p0, p1, p2, p3])
+ self.branch_1.set_pos([p4, p5, p6, p7])
+
+ @property
+ def pts(self):
+ return [self.pos_3d]
+
+ def draw(self, context, render=False):
+ self.render = render
+ self.branch_0.colour_inactive = self.colour
+ self.branch_1.colour_inactive = self.colour
+ self.branch_0.draw(context)
+ self.branch_1.draw(context)
+
+
class EditableText(GlText, GlHandle):
def __init__(self, sensor_size, size, draggable=False, selectable=False):
GlHandle.__init__(self, sensor_size, size, draggable, selectable)
@@ -783,10 +1092,10 @@ class EditableText(GlText, GlHandle):
self.pos_3d = pos_3d
self.value = value
self._text = self.add_units(context)
- x, y = self.text_size(context)
+ ts = self.text_size(context)
self.pos_2d = self.position_2d_from_coord(context, pos_3d)
- self.pos_2d.x += 0.5 * x
- self.sensor_width, self.sensor_height = 0.5 * x, y
+ self.pos_2d.x += 0.5 * ts.x
+ self.sensor_width, self.sensor_height = 0.5 * ts.x, ts.y
@property
def sensor_center(self):
@@ -796,10 +1105,10 @@ class EditableText(GlText, GlHandle):
class ThumbHandle(GlHandle):
def __init__(self, size_2d, label, image=None, draggable=False, selectable=False, d=2):
- GlHandle.__init__(self, size_2d, size_2d, draggable, selectable, d)
+ GlHandle.__init__(self, size_2d, size_2d, draggable, selectable, d, n_pts=4)
self.image = GlImage(image=image)
self.label = GlText(d=2, label=label.replace("_", " ").capitalize())
- self.frame = GlPolyline((1, 1, 1, 1), d=2)
+ self.frame = GlPolyline((1, 1, 1, 1), d=2, n_pts=4)
self.frame.closed = True
self.size_2d = size_2d
self.sensor_width = 0.5 * size_2d.x
@@ -830,7 +1139,7 @@ class ThumbHandle(GlHandle):
def draw(self, context, render=False):
self.render = render
self.image.colour_inactive = self.colour
- GlHandle.draw(self, context, render=False)
+ # GlHandle.draw(self, context, render=False)
self.image.draw(context, render=False)
self.label.draw(context, render=False)
self.frame.draw(context, render=False)
@@ -850,8 +1159,8 @@ class Screen():
x_min = self.margin
x_max = w - self.margin
if system.use_region_overlap:
+ # system.window_draw_method in {'TRIPLE_BUFFER', 'ADAPTIVEMATIC'}):
area = context.area
-
for r in area.regions:
if r.type == 'TOOLS':
x_min += r.width
@@ -865,29 +1174,30 @@ class FeedbackPanel():
Feed-back panel
inspired by np_station
"""
+
def __init__(self, title='Archipack'):
- prefs = self.get_prefs(bpy.context)
+ prefs = get_prefs(bpy.context)
self.main_title = GlText(d=2,
- label=title + " : ",
- font_size=prefs.feedback_size_main,
- colour=prefs.feedback_colour_main
- )
+ label=title + " : ",
+ font_size=prefs.feedback_size_main,
+ colour=prefs.feedback_colour_main
+ )
self.title = GlText(d=2,
- font_size=prefs.feedback_size_title,
- colour=prefs.feedback_colour_main
- )
+ font_size=prefs.feedback_size_title,
+ colour=prefs.feedback_colour_main
+ )
self.spacing = Vector((
0.5 * prefs.feedback_size_shortcut,
0.5 * prefs.feedback_size_shortcut))
self.margin = 50
self.explanation = GlText(d=2,
- font_size=prefs.feedback_size_shortcut,
- colour=prefs.feedback_colour_main
- )
- self.shortcut_area = GlPolygon(colour=prefs.feedback_shortcut_area, d=2)
- self.title_area = GlPolygon(colour=prefs.feedback_title_area, d=2)
+ font_size=prefs.feedback_size_shortcut,
+ colour=prefs.feedback_colour_main
+ )
+ self.shortcut_area = GlPolygon(colour=prefs.feedback_shortcut_area, d=2, n_pts=4)
+ self.title_area = GlPolygon(colour=prefs.feedback_title_area, d=2, n_pts=4)
self.shortcuts = []
self.on = False
self.show_title = True
@@ -902,22 +1212,11 @@ class FeedbackPanel():
def enable(self):
self.on = True
- def get_prefs(self, context):
- global __name__
- try:
- # retrieve addon name from imports
- addon_name = __name__.split('.')[0]
- prefs = context.user_preferences.addons[addon_name].preferences
- except:
- prefs = DefaultColorScheme
- pass
- return prefs
-
def instructions(self, context, title, explanation, shortcuts):
"""
position from bottom to top
"""
- prefs = self.get_prefs(context)
+ prefs = get_prefs(context)
self.explanation.label = explanation
self.title.label = title
@@ -926,16 +1225,17 @@ class FeedbackPanel():
for key, label in shortcuts:
key = GlText(d=2, label=key,
- font_size=prefs.feedback_size_shortcut,
- colour=prefs.feedback_colour_key)
+ font_size=prefs.feedback_size_shortcut,
+ colour=prefs.feedback_colour_key)
label = GlText(d=2, label=' : ' + label,
- font_size=prefs.feedback_size_shortcut,
- colour=prefs.feedback_colour_shortcut)
+ font_size=prefs.feedback_size_shortcut,
+ colour=prefs.feedback_colour_shortcut)
ks = key.text_size(context)
ls = label.text_size(context)
self.shortcuts.append([key, ks, label, ls])
def draw(self, context, render=False):
+
if self.on:
"""
draw from bottom to top
@@ -991,7 +1291,7 @@ class FeedbackPanel():
(x_max, self.margin),
(x_max, pos.y),
(x_min, pos.y)
- ]
+ ]
# small space between shortcut area and main title bar
if n_shortcuts > 0:
@@ -1002,7 +1302,7 @@ class FeedbackPanel():
(x_max, pos.y),
(x_max, pos.y + main_title_size.y + 2 * self.spacing.y),
(x_min, pos.y + main_title_size.y + 2 * self.spacing.y)
- ]
+ ]
pos.y += self.spacing.y
title_size = self.title.text_size(context)
@@ -1046,12 +1346,13 @@ class GlCursorFence():
"""
Cursor crossing Fence
"""
- def __init__(self, width=1, colour=(1.0, 1.0, 1.0, 0.5), style=bgl.GL_LINE_STIPPLE):
- self.line_x = GlLine(d=2)
+
+ def __init__(self, width=1, colour=(1.0, 1.0, 1.0, 0.5), style=2852):
+ self.line_x = GlLine(d=2, n_pts=2)
self.line_x.style = style
self.line_x.width = width
self.line_x.colour_inactive = colour
- self.line_y = GlLine(d=2)
+ self.line_y = GlLine(d=2, n_pts=2)
self.line_y.style = style
self.line_y.width = width
self.line_y.colour_inactive = colour
@@ -1060,7 +1361,8 @@ class GlCursorFence():
def set_location(self, context, location):
w = context.region.width
h = context.region.height
- x, y = location
+ p = Vector(location)
+ x, y = p.x, p.y
self.line_x.p = Vector((0, y))
self.line_x.v = Vector((w, 0))
self.line_y.p = Vector((x, 0))
@@ -1080,27 +1382,29 @@ class GlCursorFence():
class GlCursorArea():
def __init__(self,
- width=1,
- bordercolour=(1.0, 1.0, 1.0, 0.5),
- areacolour=(0.5, 0.5, 0.5, 0.08),
- style=bgl.GL_LINE_STIPPLE):
+ width=1,
+ bordercolour=(1.0, 1.0, 1.0, 0.5),
+ areacolour=(0.5, 0.5, 0.5, 0.08),
+ style=2852):
- self.border = GlPolyline(bordercolour, d=2)
+ self.border = GlPolyline(bordercolour, d=2, n_pts=4)
self.border.style = style
self.border.width = width
self.border.closed = True
- self.area = GlPolygon(areacolour, d=2)
+ self.area = GlPolygon(areacolour, d=2, n_pts=4)
self.min = Vector((0, 0))
self.max = Vector((0, 0))
self.on = False
def in_area(self, pt):
return (self.min.x <= pt.x and self.max.x >= pt.x and
- self.min.y <= pt.y and self.max.y >= pt.y)
+ self.min.y <= pt.y and self.max.y >= pt.y)
def set_location(self, context, p0, p1):
- x0, y0 = p0
- x1, y1 = p1
+ p = Vector(p0)
+ x0, y0 = p.x, p.y
+ p = Vector(p1)
+ x1, y1 = p.x, p.y
if x0 > x1:
x1, x0 = x0, x1
if y0 > y1:
diff --git a/archipack/archipack_handle.py b/archipack/archipack_handle.py
index fcdb570e..d27603b0 100644
--- a/archipack/archipack_handle.py
+++ b/archipack/archipack_handle.py
@@ -32,17 +32,17 @@ def create_handle(context, parent, mesh):
old = context.active_object
handle = bpy.data.objects.new("Handle", mesh)
handle['archipack_handle'] = True
- context.scene.objects.link(handle)
+ context.scene.collection.objects.link(handle)
modif = handle.modifiers.new('Subsurf', 'SUBSURF')
modif.render_levels = 4
modif.levels = 1
handle.parent = parent
handle.matrix_world = parent.matrix_world.copy()
- context.scene.objects.active = handle
+ context.view_layer.objects.active = handle
m = handle.archipack_material.add()
m.category = 'handle'
m.material = 'DEFAULT'
- context.scene.objects.active = old
+ context.view_layer.objects.active = old
return handle
diff --git a/archipack/archipack_keymaps.py b/archipack/archipack_keymaps.py
index c4c8176e..a30b31e9 100644
--- a/archipack/archipack_keymaps.py
+++ b/archipack/archipack_keymaps.py
@@ -24,6 +24,7 @@
# Author: Stephen Leger (s-leger)
#
# ----------------------------------------------------------
+import bpy
class Keymaps:
@@ -79,6 +80,10 @@ class Keymaps:
event: simple event signature to compare like :
if event == keymap.undo.event:
"""
+ # Headless mode fails without this check
+ if bpy.app.background:
+ return {'type': None, 'event':(False, False, False, False, None, None)}
+
ev = context.window_manager.keyconfigs.user.keymaps[keyconfig].keymap_items[keymap_item]
key = ev.type
if ev.ctrl:
@@ -89,6 +94,7 @@ class Keymaps:
key += '+SHIFT'
return {'type': key, 'name': ev.name, 'event': (ev.alt, ev.ctrl, ev.shift, ev.type, ev.value)}
+
def dump_keys(self, context, filename="c:\\tmp\\keymap.txt"):
"""
Utility for developers :
diff --git a/archipack/archipack_manipulator.py b/archipack/archipack_manipulator.py
index 5ed7312b..06efefff 100644
--- a/archipack/archipack_manipulator.py
+++ b/archipack/archipack_manipulator.py
@@ -30,7 +30,13 @@ from mathutils import Vector, Matrix
from mathutils.geometry import intersect_line_plane, intersect_point_line, intersect_line_sphere
from bpy_extras import view3d_utils
from bpy.types import PropertyGroup, Operator
-from bpy.props import FloatVectorProperty, StringProperty, CollectionProperty, BoolProperty
+from bpy.props import (
+ FloatVectorProperty,
+ StringProperty,
+ CollectionProperty,
+ BoolProperty
+)
+
from bpy.app.handlers import persistent
from .archipack_snap import snap_point
from .archipack_keymaps import Keymaps
@@ -67,14 +73,16 @@ from .archipack_gl import (
# (manips[key].manipulable.manip_stack)
# Must investigate for a way to handle unselect after drag done.
+
+import logging
+logger = logging.getLogger("archipack")
+
+
"""
- @TODO:
- Last modal running wins.
- Manipulateurs without snap and thus not running own modal,
- may loose events events caught by select mode of last
- manipulable enabled
+ Change object location when moving 1 point
+ When False, change data.origin instead
"""
-
+USE_MOVE_OBJECT = True
# Arrow sizes (world units)
arrow_size = 0.05
# Handle area size (pixels)
@@ -469,7 +477,7 @@ class Manipulator():
view_vector_mouse = view3d_utils.region_2d_to_vector_3d(region, rv3d, self.mouse_pos)
ray_origin_mouse = view3d_utils.region_2d_to_origin_3d(region, rv3d, self.mouse_pos)
pt = intersect_line_plane(ray_origin_mouse, ray_origin_mouse + view_vector_mouse,
- self.origin, rM * self.manipulator.normal, False)
+ self.origin, rM @ self.manipulator.normal, False)
# fix issue with parallel plane
if pt is None:
pt = intersect_line_plane(ray_origin_mouse, ray_origin_mouse + view_vector_mouse,
@@ -495,18 +503,19 @@ class Manipulator():
"""
try:
if self.get_value(data, attr, index) != value:
+ o = self.o
# switch context so unselected object may be manipulable too
- old = context.active_object
- state = self.o.select
- self.o.select = True
- context.scene.objects.active = self.o
+ old = context.object
+ state = o.select_get()
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
if index > -1:
getattr(data, attr)[index] = value
else:
setattr(data, attr, value)
- self.o.select = state
- old.select = True
- context.scene.objects.active = old
+ o.select_set(state=state)
+ old.select_set(state=True)
+ context.view_layer.objects.active = old
except:
pass
@@ -516,11 +525,7 @@ class Manipulator():
tM Matrix source
vec Vector translation
"""
- return tM * Matrix([
- [1, 0, 0, vec.x],
- [0, 1, 0, vec.y],
- [0, 0, 1, vec.z],
- [0, 0, 0, 1]])
+ return tM @ Matrix.Translation(vec)
def _move(self, o, axis, value):
if axis == 'x':
@@ -538,15 +543,15 @@ class Manipulator():
"""
old = context.active_object
bpy.ops.object.select_all(action='DESELECT')
- self.o.select = True
- context.scene.objects.active = self.o
+ self.o.select_set(state=True)
+ context.view_layer.objects.active = self.o
bpy.ops.object.select_linked(type='OBDATA')
for o in context.selected_objects:
if o != self.o:
self._move(o, axis, value)
bpy.ops.object.select_all(action='DESELECT')
- old.select = True
- context.scene.objects.active = old
+ old.select_set(state=True)
+ context.view_layer.objects.active = old
def move(self, context, axis, value):
"""
@@ -555,68 +560,6 @@ class Manipulator():
self._move(self.o, axis, value)
-# OUT OF ORDER
-class SnapPointManipulator(Manipulator):
- """
- np_station based snap manipulator
- dosent update anything by itself.
- NOTE : currently out of order
- and disabled in __init__
- """
- def __init__(self, context, o, datablock, manipulator, handle_size, snap_callback=None):
-
- raise NotImplementedError
-
- self.handle = SquareHandle(handle_size, 1.2 * arrow_size, draggable=True)
- Manipulator.__init__(self, context, o, datablock, manipulator, snap_callback)
-
- def check_hover(self):
- self.handle.check_hover(self.mouse_pos)
-
- def mouse_press(self, context, event):
- if self.handle.hover:
- self.handle.hover = False
- self.handle.active = True
- self.o.select = True
- # takeloc = self.o.matrix_world * self.manipulator.p0
- # print("Invoke sp_point_move %s" % (takeloc))
- # @TODO:
- # implement and add draw and callbacks
- # snap_point(takeloc, draw, callback)
- return True
- return False
-
- def mouse_release(self, context, event):
- self.check_hover()
- self.handle.active = False
- # False to callback manipulable_release
- return False
-
- def update(self, context, event):
- # NOTE:
- # dosent set anything internally
- return
-
- def mouse_move(self, context, event):
- """
-
- """
- self.mouse_position(event)
- if self.handle.active:
- # self.handle.active = np_snap.is_running
- # self.update(context)
- # True here to callback manipulable_manipulate
- return True
- else:
- self.check_hover()
- return False
-
- def draw_callback(self, _self, context, render=False):
- left, right, side, normal = self.manipulator.get_pts(self.o.matrix_world)
- self.handle.set_pos(context, left, Vector((1, 0, 0)), normal=normal)
- self.handle.draw(context, render)
-
-
# Generic snap tool for line based archipack objects (fence, wall, maybe stair too)
gl_pts3d = []
@@ -682,7 +625,7 @@ class WallSnapManipulator(Manipulator):
])
self.feedback.enable()
self.handle.hover = False
- self.o.select = True
+ self.o.select_set(state=True)
takeloc, right, side, dz = self.manipulator.get_pts(self.o.matrix_world)
dx = (right - takeloc).normalized()
dy = dz.cross(dx)
@@ -712,20 +655,20 @@ class WallSnapManipulator(Manipulator):
np station callback on moving, place, or cancel
"""
global gl_pts3d
+ logger.debug("WallSnapManipulator.sp_callback")
if state == 'SUCCESS':
-
- self.o.select = True
+ o = self.o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
# apply changes to wall
d = self.datablock
- d.auto_update = False
-
g = d.get_generator()
# rotation relative to object
- rM = self.o.matrix_world.inverted().to_3x3()
- delta = (rM * sp.delta).to_2d()
- # x_axis = (rM * Vector((1, 0, 0))).to_2d()
+ rM = o.matrix_world.inverted().to_3x3()
+ delta =rM @ sp.delta
+ # x_axis = (rM @ Vector((1, 0, 0))).to_2d()
# update generator
idx = 0
@@ -734,7 +677,7 @@ class WallSnapManipulator(Manipulator):
if selected:
# new location in object space
- pt = g.segs[idx].lerp(0) + delta
+ pt = g.segs[idx].lerp(0) + delta.to_2d()
# move last point of segment before current
if idx > 0:
@@ -747,6 +690,7 @@ class WallSnapManipulator(Manipulator):
# update properties from generator
idx = 0
+
for p0, p1, selected in gl_pts3d:
if selected:
@@ -759,7 +703,7 @@ class WallSnapManipulator(Manipulator):
if idx > 1:
part.a0 = w.delta_angle(g.segs[idx - 2])
else:
- part.a0 = w.straight(1, 0).angle
+ part.a0 = w.a0
if "C_" in part.type:
part.radius = w.r
@@ -773,10 +717,14 @@ class WallSnapManipulator(Manipulator):
if idx > 0:
part.a0 = w.delta_angle(g.segs[idx - 1])
else:
- part.a0 = w.straight(1, 0).angle
+ part.a0 = w.a0
# move object when point 0
- self.o.location += sp.delta
- self.o.matrix_world.translation += sp.delta
+ if USE_MOVE_OBJECT:
+ d.move_object(o, o.matrix_world.translation + sp.delta)
+ # self.o.location += sp.delta
+ # self.o.matrix_world.translation += sp.delta
+ else:
+ d.origin += sp.delta
if "C_" in part.type:
part.radius = w.r
@@ -790,15 +738,18 @@ class WallSnapManipulator(Manipulator):
idx += 1
self.mouse_release(context, event)
- d.auto_update = True
+ d.relocate_childs(context, o, g)
+ d.update(context)
if state == 'CANCEL':
self.mouse_release(context, event)
+ logger.debug("WallSnapManipulator.sp_callback done")
return
def sp_draw(self, sp, context):
# draw wall placeholders
+ logger.debug("WallSnapManipulator.sp_draw")
global gl_pts3d
@@ -842,6 +793,7 @@ class WallSnapManipulator(Manipulator):
self.label.set_pos(context, self.line.length, self.line.lerp(0.5), self.line.v, normal=Vector((0, 0, 1)))
self.line.draw(context, render=False)
self.label.draw(context, render=False)
+ logger.debug("WallSnapManipulator.sp_draw done")
def mouse_move(self, context, event):
self.mouse_position(event)
@@ -1002,7 +954,6 @@ class SizeManipulator(Manipulator):
])
gl_pts3d = [left, right]
snap_point(takemat=takemat,
- draw=self.sp_draw,
callback=self.sp_callback,
constraint_axis=(True, False, False))
self.handle_right.active = True
@@ -1085,32 +1036,31 @@ class SizeManipulator(Manipulator):
self.label.draw(context, render)
self.feedback.draw(context, render)
- def sp_draw(self, sp, context):
+ def sp_callback(self, context, event, state, sp):
+ logger.debug("SizeManipulator.sp_callback")
global gl_pts3d
- if self.o is None:
- return
+
p0 = gl_pts3d[0].copy()
p1 = gl_pts3d[1].copy()
- p1 += sp.delta
- self.sp_update(context, p0, p1)
- return
- def sp_callback(self, context, event, state, sp):
+ if state != 'CANCEL':
+ p1 += sp.delta
- if state == 'SUCCESS':
- self.sp_draw(sp, context)
- self.mouse_release(context, event)
+ length = (p0 - p1).length
- if state == 'CANCEL':
- p0 = gl_pts3d[0].copy()
- p1 = gl_pts3d[1].copy()
- self.sp_update(context, p0, p1)
- self.mouse_release(context, event)
+ if state != 'CANCEL' and event.alt:
+ if event.shift:
+ length = round(length, 2)
+ else:
+ length = round(length, 1)
- def sp_update(self, context, p0, p1):
- length = (p0 - p1).length
self.set_value(context, self.datablock, self.manipulator.prop1_name, length)
+ if state != 'RUNNING':
+ self.mouse_release(context, event)
+
+ logger.debug("SizeManipulator.sp_callback done")
+
class SizeLocationManipulator(SizeManipulator):
"""
@@ -1190,7 +1140,7 @@ class SizeLocationManipulator(SizeManipulator):
self.mouse_release(context, event)
# must move back to original location
itM = self.o.matrix_world.inverted()
- dl = self.get_value(itM * self.original_location, self.manipulator.prop2_name)
+ dl = self.get_value(itM @ self.original_location, self.manipulator.prop2_name)
self.move(context, self.manipulator.prop2_name, dl)
self.set_value(context, self.datablock, self.manipulator.prop1_name, self.original_size)
@@ -1263,7 +1213,6 @@ class SnapSizeLocationManipulator(SizeLocationManipulator):
])
gl_pts3d = [left, right]
snap_point(takemat=takemat,
- draw=self.sp_draw,
callback=self.sp_callback,
constraint_axis=(True, False, False))
@@ -1290,7 +1239,6 @@ class SnapSizeLocationManipulator(SizeLocationManipulator):
])
gl_pts3d = [left, right]
snap_point(takemat=takemat,
- draw=self.sp_draw,
callback=self.sp_callback,
constraint_axis=(True, False, False))
self.handle_left.active = True
@@ -1305,50 +1253,50 @@ class SnapSizeLocationManipulator(SizeLocationManipulator):
return False
- def sp_draw(self, sp, context):
+ def sp_callback(self, context, event, state, sp):
+ logger.debug("SnapSizeLocationManipulator.sp_callback")
global gl_pts3d
- if self.o is None:
- return
p0 = gl_pts3d[0].copy()
p1 = gl_pts3d[1].copy()
- if self.handle_right.active:
- p1 += sp.delta
- else:
- p0 += sp.delta
- self.sp_update(context, p0, p1)
-
- # snapping child objects may require base object update
- # eg manipulating windows requiring wall update
- if self.snap_callback is not None:
- snap_helper = context.active_object
- self.snap_callback(context, o=self.o, manipulator=self)
- context.scene.objects.active = snap_helper
-
- return
-
- def sp_callback(self, context, event, state, sp):
- if state == 'SUCCESS':
- self.sp_draw(sp, context)
- self.mouse_release(context, event)
-
- if state == 'CANCEL':
- p0 = gl_pts3d[0].copy()
- p1 = gl_pts3d[1].copy()
- self.sp_update(context, p0, p1)
- self.mouse_release(context, event)
+ if state != 'CANCEL':
+ if self.handle_right.active:
+ p1 += sp.delta
+ else:
+ p0 += sp.delta
- def sp_update(self, context, p0, p1):
l0 = self.get_value(self.datablock, self.manipulator.prop1_name)
length = (p0 - p1).length
+
+ if state != 'CANCEL' and event.alt:
+ if event.shift:
+ length = round(length, 2)
+ else:
+ length = round(length, 1)
+
dp = length - l0
+
if self.handle_left.active:
dp = -dp
dl = 0.5 * dp
+
+ # snap_helper = context.object
self.move(context, self.manipulator.prop2_name, dl)
self.set_value(context, self.datablock, self.manipulator.prop1_name, length)
self.move_linked(context, self.manipulator.prop2_name, dl)
+ # snapping child objects may require base object update
+ # eg manipulating windows requiring wall update
+ if self.snap_callback is not None:
+ snap_helper = context.active_object
+ self.snap_callback(context, o=self.o, manipulator=self)
+ snap_helper.select_set(state=True)
+
+ if state != 'RUNNING':
+ self.mouse_release(context, event)
+
+ logger.debug("SnapSizeLocationManipulator.sp_callback done")
+
class DeltaLocationManipulator(SizeManipulator):
"""
@@ -1388,7 +1336,6 @@ class DeltaLocationManipulator(SizeManipulator):
])
gl_pts3d = [p0]
snap_point(takemat=takemat,
- draw=self.sp_draw,
callback=self.sp_callback,
constraint_axis=(
self.manipulator.prop1_name == 'x',
@@ -1413,40 +1360,37 @@ class DeltaLocationManipulator(SizeManipulator):
self.check_hover()
return False
- def sp_draw(self, sp, context):
- global gl_pts3d
- if self.o is None:
- return
- p0 = gl_pts3d[0].copy()
- p1 = p0 + sp.delta
- itM = self.o.matrix_world.inverted()
- dl = self.get_value(itM * p1, self.manipulator.prop1_name)
- self.move(context, self.manipulator.prop1_name, dl)
-
- # snapping child objects may require base object update
- # eg manipulating windows requiring wall update
- if self.snap_callback is not None:
- snap_helper = context.active_object
- self.snap_callback(context, o=self.o, manipulator=self)
- context.scene.objects.active = snap_helper
-
- return
-
def sp_callback(self, context, event, state, sp):
-
- if state == 'SUCCESS':
- self.sp_draw(sp, context)
- self.mouse_release(context, event)
+ logger.debug("DeltaLocationManipulator.sp_callback")
if state == 'CANCEL':
self.cancel(context, event)
+ else:
+ global gl_pts3d
+ p0 = gl_pts3d[0].copy()
+ p1 = p0 + sp.delta
+ itM = self.o.matrix_world.inverted()
+ dl = self.get_value(itM @ p1, self.manipulator.prop1_name)
+ self.move(context, self.manipulator.prop1_name, dl)
+
+ # snapping child objects may require base object update
+ # eg manipulating windows requiring wall update
+ if self.snap_callback is not None:
+ snap_helper = context.active_object
+ self.snap_callback(context, o=self.o, manipulator=self)
+ snap_helper.select_set(state=True)
+
+ if state == 'SUCCESS':
+ self.mouse_release(context, event)
+
+ logger.debug("DeltaLocationManipulator.sp_callback done")
def cancel(self, context, event):
if self.active:
self.mouse_release(context, event)
# must move back to original location
itM = self.o.matrix_world.inverted()
- dl = self.get_value(itM * self.original_location, self.manipulator.prop1_name)
+ dl = self.get_value(itM @ self.original_location, self.manipulator.prop1_name)
self.move(context, self.manipulator.prop1_name, dl)
def draw_callback(self, _self, context, render=False):
@@ -1963,22 +1907,22 @@ class archipack_manipulator(PropertyGroup):
p0, p1, p2 3d Vectors as base points to represent manipulators on screen
normal Vector normal of plane on with draw manipulator
"""
- type_key = StringProperty(default='SIZE')
+ type_key : StringProperty(default='SIZE')
# How 3d points are stored in manipulators ?
# SIZE = 2 absolute positioned and a scaling vector
# RADIUS = 1 absolute positioned (center) and 2 relatives (sides)
# POLYGON = 2 absolute positioned and a relative vector (for rect polygons)
- pts_mode = StringProperty(default='SIZE')
- prop1_name = StringProperty()
- prop2_name = StringProperty()
- p0 = FloatVectorProperty(subtype='XYZ')
- p1 = FloatVectorProperty(subtype='XYZ')
- p2 = FloatVectorProperty(subtype='XYZ')
+ pts_mode : StringProperty(default='SIZE')
+ prop1_name : StringProperty()
+ prop2_name : StringProperty()
+ p0 : FloatVectorProperty(subtype='XYZ')
+ p1 : FloatVectorProperty(subtype='XYZ')
+ p2 : FloatVectorProperty(subtype='XYZ')
# allow orientation of manipulators by default on xy plane,
# but may be used to constrain heights on local object space
- normal = FloatVectorProperty(subtype='XYZ', default=(0, 0, 1))
+ normal : FloatVectorProperty(subtype='XYZ', default=(0, 0, 1))
def set_pts(self, pts, normal=None):
"""
@@ -1999,9 +1943,9 @@ class archipack_manipulator(PropertyGroup):
"""
rM = tM.to_3x3()
if self.pts_mode in ['SIZE', 'POLYGON']:
- return tM * self.p0, tM * self.p1, self.p2, rM * self.normal
+ return tM @ self.p0, tM @ self.p1, self.p2, rM @ self.normal
else:
- return tM * self.p0, rM * self.p1, rM * self.p2, rM * self.normal
+ return tM @ self.p0, rM @ self.p1, rM @ self.p2, rM @ self.normal
def get_prefs(self, context):
global __name__
@@ -2053,7 +1997,7 @@ class ARCHIPACK_OT_manipulate(Operator):
bl_description = "Manipulate"
bl_options = {'REGISTER', 'UNDO'}
- object_name = StringProperty(default="")
+ object_name : StringProperty(default="")
@classmethod
def poll(self, context):
@@ -2123,38 +2067,39 @@ class Manipulable():
Beware : prevent crash calling manipulable_disable()
before changing manipulated data structure
"""
- manipulators = CollectionProperty(
+ manipulators : CollectionProperty(
type=archipack_manipulator,
# options={'SKIP_SAVE'},
# options={'HIDDEN'},
description="store 3d points to draw gl manipulators"
)
- manipulable_refresh = BoolProperty(
+
+ # TODO: make simple instance vars
+ manipulable_refresh : BoolProperty(
default=False,
options={'SKIP_SAVE'},
description="Flag enable to rebuild manipulators when data model change"
)
- manipulate_mode = BoolProperty(
+ manipulate_mode : BoolProperty(
default=False,
options={'SKIP_SAVE'},
description="Flag manipulation state so we are able to toggle"
)
- select_mode = BoolProperty(
+ select_mode : BoolProperty(
default=False,
options={'SKIP_SAVE'},
description="Flag select state so we are able to toggle"
)
- manipulable_selectable = BoolProperty(
+ manipulable_selectable : BoolProperty(
default=False,
options={'SKIP_SAVE'},
description="Flag make manipulators selectable"
)
- keymap = None
- # selectable manipulators
- manipulable_area = GlCursorArea()
- manipulable_start_point = Vector((0, 0))
- manipulable_end_point = Vector((0, 0))
+ keymap = None
+ manipulable_area = None
+ manipulable_start_point = None
+ manipulable_end_point = None
manipulable_draw_handler = None
def setup_manipulators(self):
@@ -2171,6 +2116,13 @@ class Manipulable():
"""
disable gl draw handlers
"""
+
+ if self.keymap is None:
+ self.keymap = Keymaps(context)
+ self.manipulable_area = GlCursorArea()
+ self.manipulable_start_point = Vector((0, 0))
+ self.manipulable_end_point = Vector((0, 0))
+
o = context.active_object
if o is not None:
self.manipulable_exit_selectmode(context)
@@ -2259,6 +2211,7 @@ class Manipulable():
as it provide all needed
functionality out of the box
"""
+
# setup again when manipulators type change
if self.manipulable_refresh:
# print("manipulable_refresh")
diff --git a/archipack/archipack_material.py b/archipack/archipack_material.py
index ddb44009..2bcd3e40 100644
--- a/archipack/archipack_material.py
+++ b/archipack/archipack_material.py
@@ -181,7 +181,7 @@ class MatlibsManager():
def apply(self, context, slot_index, name, link=False):
o = context.active_object
- o.select = True
+ o.select_set(state=True)
# material with same name exist in scene
mat = self.from_data(name)
@@ -367,12 +367,12 @@ def update(self, context):
class archipack_material(PropertyGroup):
- category = StringProperty(
+ category : StringProperty(
name="Category",
description="Archipack object name",
default=""
)
- material = EnumProperty(
+ material : EnumProperty(
name="Material",
description="Material Set name",
items=material_enum,
@@ -415,13 +415,13 @@ class archipack_material(PropertyGroup):
return False
for ob in sel:
- context.scene.objects.active = ob
+ context.view_layer.objects.active = ob
for slot_index, mat_name in enumerate(mats):
if slot_index >= len(ob.material_slots):
bpy.ops.object.material_slot_add()
self.apply_material(context, slot_index, mat_name)
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
return True
@@ -431,7 +431,7 @@ class ARCHIPACK_PT_material(Panel):
bl_label = "Archipack Material"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- # bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -442,8 +442,8 @@ class ARCHIPACK_PT_material(Panel):
props = context.active_object.archipack_material[0]
row = layout.row(align=True)
row.prop(props, 'material', text="")
- row.operator('archipack.material_add', icon="ZOOMIN", text="")
- row.operator('archipack.material_remove', icon="ZOOMOUT", text="")
+ row.operator('archipack.material_add', icon="ADD", text="")
+ row.operator('archipack.material_remove', icon="REMOVE", text="")
class ARCHIPACK_OT_material(Operator):
@@ -452,12 +452,12 @@ class ARCHIPACK_OT_material(Operator):
bl_description = "Add archipack material"
bl_options = {'REGISTER', 'UNDO'}
- category = StringProperty(
+ category : StringProperty(
name="Category",
description="Archipack object name",
default=""
)
- material = StringProperty(
+ material : StringProperty(
name="Material",
description="Material Set name",
default=""
@@ -499,7 +499,7 @@ class ARCHIPACK_OT_material_add(Operator):
bl_description = "Add a set of archipack material"
bl_options = {'REGISTER', 'UNDO'}
- material = StringProperty(
+ material : StringProperty(
name="Material",
description="Material Set name",
default=""
@@ -603,5 +603,5 @@ def unregister():
bpy.utils.unregister_class(ARCHIPACK_OT_material_add)
bpy.utils.unregister_class(ARCHIPACK_OT_material_remove)
bpy.utils.unregister_class(ARCHIPACK_OT_material_library)
- bpy.utils.unregister_class(archipack_material)
del Object.archipack_material
+ bpy.utils.unregister_class(archipack_material)
diff --git a/archipack/archipack_object.py b/archipack/archipack_object.py
index b479ea30..10da5be1 100644
--- a/archipack/archipack_object.py
+++ b/archipack/archipack_object.py
@@ -100,6 +100,7 @@ class ArchipackObject():
selected = context.selected_objects[:]
for o in selected:
+
if self.__class__.datablock(o) == self:
self.previously_selected = selected
self.previously_active = active
@@ -113,27 +114,41 @@ class ArchipackObject():
try:
for o in self.previously_selected:
- o.select = True
+ o.select_set(state=True)
except:
pass
if self.previously_active is not None:
- self.previously_active.select = True
- context.scene.objects.active = self.previously_active
+ self.previously_active.select_set(state=True)
+ context.view_layer.objects.active = self.previously_active
self.previously_selected = None
self.previously_active = None
+ def move_object(self, o, p):
+ """
+ When firstpoint is moving we must move object according
+ p is new x, y location in world coordsys
+ """
+ p = Vector((p.x, p.y, o.matrix_world.translation.z))
+ # p is in o coordsys
+ if o.parent:
+ o.location = p @ o.parent.matrix_world.inverted()
+ o.matrix_world.translation = p
+ else:
+ o.location = p
+ o.matrix_world.translation = p
+
class ArchipackCreateTool():
"""
Shared property of archipack's create tool Operator
"""
- auto_manipulate = BoolProperty(
+ auto_manipulate : BoolProperty(
name="Auto manipulate",
description="Enable object's manipulators after create",
options={'SKIP_SAVE'},
default=True
)
- filepath = StringProperty(
+ filepath : StringProperty(
options={'SKIP_SAVE'},
name="Preset",
description="Full filename of python preset to load at create time",
@@ -164,7 +179,10 @@ class ArchipackCreateTool():
if fallback:
# fallback to load preset on background process
try:
- exec(compile(open(self.filepath).read(), self.filepath, 'exec'))
+ with open(self.filepath) as f:
+ lines = f.read()
+ cmp = compile(lines, self.filepath, 'exec')
+ exec(cmp)
except:
print("Archipack unable to load preset file : %s" % (self.filepath))
pass
@@ -194,7 +212,7 @@ class ArchipackCreateTool():
pass
-class ArchpackDrawTool():
+class ArchipackDrawTool():
"""
Draw tools
"""
@@ -225,8 +243,9 @@ class ArchpackDrawTool():
view_vector_mouse = region_2d_to_vector_3d(region, rv3d, co2d)
ray_origin_mouse = region_2d_to_origin_3d(region, rv3d, co2d)
res, pos, normal, face_index, object, matrix_world = context.scene.ray_cast(
- ray_origin_mouse,
- view_vector_mouse)
+ view_layer=context.view_layer,
+ origin=ray_origin_mouse,
+ direction=view_vector_mouse)
return res, pos, normal, face_index, object, matrix_world
def mouse_hover_wall(self, context, event):
@@ -245,5 +264,5 @@ class ArchpackDrawTool():
[x.y, y.y, z.y, pt.y],
[x.z, y.z, z.z, o.matrix_world.translation.z],
[0, 0, 0, 1]
- ]), o, y
- return False, Matrix(), None, Vector()
+ ]), o, d.width, y, 0 # d.z_offset
+ return False, Matrix(), None, 0, Vector(), 0
diff --git a/archipack/archipack_preset.py b/archipack/archipack_preset.py
index dcaa7970..42668bb9 100644
--- a/archipack/archipack_preset.py
+++ b/archipack/archipack_preset.py
@@ -170,7 +170,9 @@ class PresetMenuItem():
def __init__(self, thumbsize, preset, image=None):
name = bpy.path.display_name_from_filepath(preset)
self.preset = preset
- self.handle = ThumbHandle(thumbsize, name, image, draggable=True)
+ self.image = image
+ self.image.gl_load()
+ self.handle = ThumbHandle(thumbsize, name, self.image, draggable=True)
self.enable = True
def filter(self, keywords):
@@ -179,6 +181,11 @@ class PresetMenuItem():
return False
return True
+ def cleanup(self):
+ if self.image:
+ self.image.gl_free()
+ # bpy.data.images.remove(self.image)
+
def set_pos(self, context, pos):
self.handle.set_pos(context, pos)
@@ -268,12 +275,15 @@ class PresetMenu():
return file_list
def clearImages(self):
+ for item in self.menuItems:
+ item.cleanup()
for image in bpy.data.images:
if image.filepath_raw in self.imageList:
# image.user_clear()
bpy.data.images.remove(image, do_unlink=True)
self.imageList.clear()
+
def make_menuitem(self, filepath):
"""
@TODO:
@@ -377,7 +387,7 @@ class PresetMenu():
class PresetMenuOperator():
- preset_operator = StringProperty(
+ preset_operator : StringProperty(
options={'SKIP_SAVE'},
default="script.execute_preset"
)
@@ -414,7 +424,11 @@ class PresetMenuOperator():
if self.preset_operator == 'script.execute_preset':
# call from preset menu
# ensure right active_object class
- d = getattr(bpy.types, self.preset_subdir).datablock(context.active_object)
+ o = context.active_object
+ if o.data and self.preset_subdir in o.data:
+ d = getattr(o.data, self.preset_subdir)[0]
+ elif self.preset_subdir in o:
+ d = getattr(o, self.preset_subdir)[0]
if d is not None:
d.auto_update = False
# print("Archipack execute_preset loading auto_update:%s" % d.auto_update)
@@ -525,16 +539,22 @@ class ArchipackPreset(AddPresetBase):
def background_render(self, context, cls, preset):
generator = os.path.dirname(os.path.realpath(__file__)) + os.path.sep + "archipack_thumbs.py"
+ addon_name = __name__.split('.')[0]
+ matlib_path = context.user_preferences.addons[addon_name].preferences.matlib_path
# Run external instance of blender like the original thumbnail generator.
cmd = [
bpy.app.binary_path,
"--background",
+ "--factory-startup",
"-noaudio",
+ # "--addons", addon_name,
"--python", generator,
"--",
+ "addon:" + addon_name,
+ "matlib:" + matlib_path,
"cls:" + cls,
"preset:" + preset
- ]
+ ]
# print(repr(cmd))
subprocess.Popen(cmd)
@@ -555,7 +575,7 @@ class ArchipackPreset(AddPresetBase):
preset = os.path.join(target_path, filename) + ".py"
cls = self.preset_subdir[10:]
- print("post cb cls:%s preset:%s" % (cls, preset))
+ # print("post cb cls:%s preset:%s" % (cls, preset))
self.background_render(context, cls, preset)
return
diff --git a/archipack/archipack_reference_point.py b/archipack/archipack_reference_point.py
index 2f58c088..fe27b224 100644
--- a/archipack/archipack_reference_point.py
+++ b/archipack/archipack_reference_point.py
@@ -41,22 +41,22 @@ def update(self, context):
class archipack_reference_point(PropertyGroup):
- location_2d = FloatVectorProperty(
+ location_2d : FloatVectorProperty(
subtype='XYZ',
name="position 2d",
default=Vector((0, 0, 0))
)
- location_3d = FloatVectorProperty(
+ location_3d : FloatVectorProperty(
subtype='XYZ',
name="position 3d",
default=Vector((0, 0, 0))
)
- symbol_scale = FloatProperty(
+ symbol_scale : FloatProperty(
name="Screen scale",
default=1,
min=0.01,
update=update)
- symbol_type = EnumProperty(
+ symbol_type : EnumProperty(
name="Symbol type",
default='WALL',
items=(
@@ -177,7 +177,7 @@ class ARCHIPACK_PT_reference_point(Panel):
bl_label = "Reference point"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -206,12 +206,12 @@ class ARCHIPACK_OT_reference_point(Operator):
bl_description = "Add reference point"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- location_3d = FloatVectorProperty(
+ location_3d : FloatVectorProperty(
subtype='XYZ',
name="position 3d",
default=Vector((0, 0, 0))
)
- symbol_type = EnumProperty(
+ symbol_type : EnumProperty(
name="Symbol type",
default='WALL',
items=(
@@ -226,7 +226,7 @@ class ARCHIPACK_OT_reference_point(Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
x, y, z = context.scene.cursor_location
@@ -234,21 +234,21 @@ class ARCHIPACK_OT_reference_point(Operator):
m = bpy.data.meshes.new(name="Reference")
o = bpy.data.objects.new("Reference", m)
o.location = Vector((x, y, 0))
- context.scene.objects.link(o)
+ context.scene.collection.objects.link(o)
d = o.archipack_reference_point.add()
d.location_2d = Vector((x, y, 0))
d.location_3d = self.location_3d
d.symbol_type = self.symbol_type
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
d.update(context)
return o
def execute(self, context):
if context.mode == "OBJECT":
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -298,7 +298,7 @@ class ARCHIPACK_OT_apply_holes(Operator):
ctx['modifier'] = mod
try:
bpy.ops.object.modifier_apply(ctx, apply_as='DATA',
- modifier=ctx['modifier'].name)
+ modifier=mod.name)
except:
pass
@@ -327,12 +327,12 @@ class ARCHIPACK_OT_apply_holes(Operator):
bpy.ops.object.select_all(action="DESELECT")
for r in to_remove:
r.hide_select = False
- r.select = True
- context.scene.objects.active = r
+ r.select_set(state=True)
+ context.view_layer.objects.active = r
bpy.ops.object.delete(use_global=False)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
@@ -410,9 +410,9 @@ class ARCHIPACK_OT_move_2d_reference_to_cursor(Operator):
bpy.ops.object.select_all(action="DESELECT")
bpy.ops.archipack.reference_point(location_3d=props.location_3d)
for child in o.children:
- child.select = True
+ child.select_set(state=True)
bpy.ops.archipack.parent_to_reference()
- context.scene.objects.unlink(o)
+ context.scene.collection.objects.unlink(o)
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -441,7 +441,7 @@ class ARCHIPACK_OT_parent_to_reference(Operator):
# print("parent_to_reference parenting:%s objects" % (len(sel)))
for child in sel:
rs = child.matrix_world.to_3x3().to_4x4()
- loc = itM * child.matrix_world.translation
+ loc = itM @ child.matrix_world.translation
child.parent = None
child.matrix_parent_inverse.identity()
child.location = Vector((0, 0, 0))
diff --git a/archipack/archipack_rendering.py b/archipack/archipack_rendering.py
index 8ea06ef9..533afffc 100644
--- a/archipack/archipack_rendering.py
+++ b/archipack/archipack_rendering.py
@@ -31,15 +31,14 @@ import bpy
# noinspection PyUnresolvedReferences
import bgl
from shutil import copyfile
-from os import path, remove, listdir
-from sys import exc_info
+from os import path, listdir
import subprocess
# noinspection PyUnresolvedReferences
import bpy_extras.image_utils as img_utils
# noinspection PyUnresolvedReferences
from math import ceil
from bpy.types import Operator
-from bl_ui import properties_render
+# from bl_ui import properties_render
class ARCHIPACK_OT_render_thumbs(Operator):
@@ -51,8 +50,8 @@ class ARCHIPACK_OT_render_thumbs(Operator):
@classmethod
def poll(cls, context):
# Ensure CYCLES engine is available
- return context.scene.archipack_progress < 0 and \
- 'CYCLES' in properties_render.RENDER_PT_render.COMPAT_ENGINES
+ # hasattr(context.scene, 'cycles')
+ return context.scene
def background_render(self, context, cls, preset):
generator = path.dirname(path.realpath(__file__)) + path.sep + "archipack_thumbs.py"
@@ -64,6 +63,7 @@ class ARCHIPACK_OT_render_thumbs(Operator):
"--background",
"--factory-startup",
"-noaudio",
+ # "--addons", addon_name,
"--python", generator,
"--",
"addon:" + addon_name,
@@ -71,6 +71,9 @@ class ARCHIPACK_OT_render_thumbs(Operator):
"cls:" + cls,
"preset:" + preset
]
+
+ # print(" ".join(cmd))
+
popen = subprocess.Popen(cmd, stdout=subprocess.PIPE, universal_newlines=True)
for stdout_line in iter(popen.stdout.readline, ""):
yield stdout_line
@@ -158,12 +161,16 @@ class ARCHIPACK_OT_render_thumbs(Operator):
for i, preset in enumerate(file_list):
dir, file = preset
cls = dir[10:]
- context.scene.archipack_progress = (100 * i / ttl)
+ # context.scene.archipack_progress = (100 * i / ttl)
+ log_all = False
for l in self.background_render(context, cls, file + ".py"):
if "[log]" in l:
print(l[5:].strip())
- # elif not "Fra:1" in l:
- # print(l.strip())
+ elif "blender.crash" in l:
+ print("Unexpected error")
+ log_all = True
+ if log_all:
+ print(l.strip())
def invoke(self, context, event):
addon_name = __name__.split('.')[0]
@@ -174,504 +181,16 @@ class ARCHIPACK_OT_render_thumbs(Operator):
return context.window_manager.invoke_confirm(self, event)
def execute(self, context):
- context.scene.archipack_progress_text = 'Generating thumbs'
- context.scene.archipack_progress = 0
+ # context.scene.archipack_progress_text = 'Generating thumbs'
+ # context.scene.archipack_progress = 0
self.rebuild_thumbs(context)
- context.scene.archipack_progress = -1
+ # context.scene.archipack_progress = -1
return {'FINISHED'}
-# -------------------------------------------------------------
-# Defines button for render
-#
-# -------------------------------------------------------------
-class ARCHIPACK_OT_render(Operator):
- bl_idname = "archipack.render"
- bl_label = "Render"
- bl_category = 'Archipack'
- bl_description = "Create a render image with measures. Use UV/Image editor to view image generated"
- bl_category = 'Archipack'
-
- # --------------------------------------------------------------------
- # Get the final render image and return as image object
- #
- # return None if no render available
- # --------------------------------------------------------------------
-
- def get_render_image(self, outpath):
- saved = False
- # noinspection PyBroadException
- try:
- # noinspection PyBroadException
- try:
- result = bpy.data.images['Render Result']
- if result.has_data is False:
- # this save produce to fill data image
- result.save_render(outpath)
- saved = True
- except:
- print("No render image found")
- return None
-
- # Save and reload
- if saved is False:
- result.save_render(outpath)
-
- img = img_utils.load_image(outpath)
-
- return img
- except:
- print("Unexpected render image error")
- return None
-
- # -------------------------------------
- # Save image to file
- # -------------------------------------
-
- def save_image(self, filepath, myimage):
- # noinspection PyBroadException
- try:
-
- # Save old info
- settings = bpy.context.scene.render.image_settings
- myformat = settings.file_format
- mode = settings.color_mode
- depth = settings.color_depth
-
- # Apply new info and save
- settings.file_format = 'PNG'
- settings.color_mode = "RGBA"
- settings.color_depth = '8'
- myimage.save_render(filepath)
- print("Archipack: Image " + filepath + " saved")
-
- # Restore old info
- settings.file_format = myformat
- settings.color_mode = mode
- settings.color_depth = depth
- except:
- print("Unexpected error:" + str(exc_info()))
- self.report({'ERROR'}, "Archipack: Unable to save render image")
- return
-
- # -------------------------------------------------------------
- # Render image main entry point
- #
- # -------------------------------------------------------------
-
- def render_main(self, context, objlist, animation=False):
- # noinspection PyBroadException,PyBroadException
- # Save old info
- scene = context.scene
- render = scene.render
- settings = render.image_settings
- depth = settings.color_depth
- settings.color_depth = '8'
- # noinspection PyBroadException
- try:
-
- # Get visible layers
- layers = []
- for x in range(0, 20):
- if scene.layers[x] is True:
- layers.extend([x])
-
- # --------------------
- # Get resolution
- # --------------------
- render_scale = render.resolution_percentage / 100
-
- width = int(render.resolution_x * render_scale)
- height = int(render.resolution_y * render_scale)
- # ---------------------------------------
- # Get output path
- # ---------------------------------------
- temp_path = path.realpath(bpy.app.tempdir)
- if len(temp_path) > 0:
- outpath = path.join(temp_path, "archipack_tmp_render.png")
- else:
- self.report({'ERROR'},
- "Archipack: Unable to save temporary render image. Define a valid temp path")
- settings.color_depth = depth
- return False
-
- # Get Render Image
- img = self.get_render_image(outpath)
- if img is None:
- self.report({'ERROR'},
- "Archipack: Unable to save temporary render image. Define a valid temp path")
- settings.color_depth = depth
- return False
-
- # -----------------------------
- # Calculate rows and columns
- # -----------------------------
- tile_x = 240
- tile_y = 216
- row_num = ceil(height / tile_y)
- col_num = ceil(width / tile_x)
- print("Archipack: Image divided in " + str(row_num) + "x" + str(col_num) + " tiles")
-
- # pixels out of visible area
- cut4 = (col_num * tile_x * 4) - width * 4 # pixels aout of drawing area
- totpixel4 = width * height * 4 # total pixels RGBA
-
- viewport_info = bgl.Buffer(bgl.GL_INT, 4)
- bgl.glGetIntegerv(bgl.GL_VIEWPORT, viewport_info)
-
- # Load image on memory
- img.gl_load(0, bgl.GL_NEAREST, bgl.GL_NEAREST)
-
- # 2.77 API change
- if bpy.app.version >= (2, 77, 0):
- tex = img.bindcode[0]
- else:
- tex = img.bindcode
-
- # --------------------------------------------
- # Create output image (to apply texture)
- # --------------------------------------------
- if "archipack_output" in bpy.data.images:
- out_img = bpy.data.images["archipack_output"]
- if out_img is not None:
- # out_img.user_clear()
- bpy.data.images.remove(out_img, do_unlink=True)
-
- out = bpy.data.images.new("archipack_output", width, height)
- tmp_pixels = [1] * totpixel4
-
- # --------------------------------
- # Loop for all tiles
- # --------------------------------
- for row in range(0, row_num):
- for col in range(0, col_num):
- buffer = bgl.Buffer(bgl.GL_FLOAT, width * height * 4)
- bgl.glDisable(bgl.GL_SCISSOR_TEST) # if remove this line, get blender screenshot not image
- bgl.glViewport(0, 0, tile_x, tile_y)
-
- bgl.glMatrixMode(bgl.GL_PROJECTION)
- bgl.glLoadIdentity()
-
- # defines ortographic view for single tile
- x1 = tile_x * col
- y1 = tile_y * row
- bgl.gluOrtho2D(x1, x1 + tile_x, y1, y1 + tile_y)
-
- # Clear
- bgl.glClearColor(0.0, 0.0, 0.0, 0.0)
- bgl.glClear(bgl.GL_COLOR_BUFFER_BIT | bgl.GL_DEPTH_BUFFER_BIT)
-
- bgl.glEnable(bgl.GL_TEXTURE_2D)
- bgl.glBindTexture(bgl.GL_TEXTURE_2D, tex)
-
- # defines drawing area
- bgl.glBegin(bgl.GL_QUADS)
-
- bgl.glColor3f(1.0, 1.0, 1.0)
- bgl.glTexCoord2f(0.0, 0.0)
- bgl.glVertex2f(0.0, 0.0)
-
- bgl.glTexCoord2f(1.0, 0.0)
- bgl.glVertex2f(width, 0.0)
-
- bgl.glTexCoord2f(1.0, 1.0)
- bgl.glVertex2f(width, height)
-
- bgl.glTexCoord2f(0.0, 1.0)
- bgl.glVertex2f(0.0, height)
-
- bgl.glEnd()
-
- # -----------------------------
- # Loop to draw all lines
- # -----------------------------
- for o, d in objlist:
- if o.hide is False:
- # verify visible layer
- for x in range(0, 20):
- if o.layers[x] is True:
- if x in layers:
- context.scene.objects.active = o
- # print("%s: %s" % (o.name, d.manip_stack))
- manipulators = d.manip_stack
- if manipulators is not None:
- for m in manipulators:
- if m is not None:
- m.draw_callback(m, context, render=True)
- break
-
- # -----------------------------
- # Loop to draw all debug
- # -----------------------------
- """
- if scene.archipack_debug is True:
- selobj = bpy.context.selected_objects
- for myobj in selobj:
- if scene.archipack_debug_vertices is True:
- draw_vertices(context, myobj, None, None)
- if scene.archipack_debug_faces is True or scene.archipack_debug_normals is True:
- draw_faces(context, myobj, None, None)
- """
- """
- if scene.archipack_rf is True:
- bgl.glColor3f(1.0, 1.0, 1.0)
- rfcolor = scene.archipack_rf_color
- rfborder = scene.archipack_rf_border
- rfline = scene.archipack_rf_line
-
- bgl.glLineWidth(rfline)
- bgl.glColor4f(rfcolor[0], rfcolor[1], rfcolor[2], rfcolor[3])
-
- x1 = rfborder
- x2 = width - rfborder
- y1 = int(ceil(rfborder / (width / height)))
- y2 = height - y1
- draw_rectangle((x1, y1), (x2, y2))
- """
- # --------------------------------
- # copy pixels to temporary area
- # --------------------------------
- bgl.glFinish()
- bgl.glReadPixels(0, 0, width, height, bgl.GL_RGBA, bgl.GL_FLOAT, buffer) # read image data
- for y in range(0, tile_y):
- # final image pixels position
- p1 = (y * width * 4) + (row * tile_y * width * 4) + (col * tile_x * 4)
- p2 = p1 + (tile_x * 4)
- # buffer pixels position
- b1 = y * width * 4
- b2 = b1 + (tile_x * 4)
-
- if p1 < totpixel4: # avoid pixel row out of area
- if col == col_num - 1: # avoid pixel columns out of area
- p2 -= cut4
- b2 -= cut4
-
- tmp_pixels[p1:p2] = buffer[b1:b2]
-
- # -----------------------
- # Copy temporary to final
- # -----------------------
- out.pixels = tmp_pixels[:] # Assign image data
- img.gl_free() # free opengl image memory
-
- # delete image
- # img.user_clear()
- bpy.data.images.remove(img, do_unlink=True)
- # remove temp file
- remove(outpath)
- # reset
- bgl.glEnable(bgl.GL_SCISSOR_TEST)
- # -----------------------
- # restore opengl defaults
- # -----------------------
- bgl.glLineWidth(1)
- bgl.glDisable(bgl.GL_BLEND)
- bgl.glColor4f(0.0, 0.0, 0.0, 1.0)
- # Saves image
- if out is not None:
- # and (scene.archipack_render is True or animation is True):
- ren_path = bpy.context.scene.render.filepath
- filename = "ap_frame"
- if len(ren_path) > 0:
- if ren_path.endswith(path.sep):
- initpath = path.realpath(ren_path) + path.sep
- else:
- (initpath, filename) = path.split(ren_path)
-
- ftxt = "%04d" % scene.frame_current
- outpath = path.realpath(path.join(initpath, filename + ftxt + ".png"))
-
- self.save_image(outpath, out)
-
- settings.color_depth = depth
- return True
-
- except:
- settings.color_depth = depth
- print("Unexpected error:" + str(exc_info()))
- self.report(
- {'ERROR'},
- "Archipack: Unable to create render image. Be sure the output render path is correct"
- )
- return False
-
- def get_objlist(self, context):
- """
- Get objects with gl manipulators
- """
- objlist = []
- for o in context.scene.objects:
- if o.data is not None:
- d = None
- if 'archipack_window' in o.data:
- d = o.data.archipack_window[0]
- elif 'archipack_door' in o.data:
- d = o.data.archipack_door[0]
- elif 'archipack_wall2' in o.data:
- d = o.data.archipack_wall2[0]
- elif 'archipack_stair' in o.data:
- d = o.data.archipack_stair[0]
- elif 'archipack_fence' in o.data:
- d = o.data.archipack_fence[0]
- elif 'archipack_floor' in o.data:
- d = o.data.archipack_floor[0]
- elif 'archipack_roof' in o.data:
- d = o.data.archipack_roof[0]
- if d is not None:
- objlist.append((o, d))
- return objlist
-
- def draw_gl(self, context):
- objlist = self.get_objlist(context)
- for o, d in objlist:
- context.scene.objects.active = o
- d.manipulable_disable(context)
- d.manipulable_invoke(context)
- return objlist
-
- def hide_gl(self, context, objlist):
- for o, d in objlist:
- context.scene.objects.active = o
- d.manipulable_disable(context)
-
- # ------------------------------
- # Execute button action
- # ------------------------------
- # noinspection PyMethodMayBeStatic,PyUnusedLocal
- def execute(self, context):
- scene = context.scene
- wm = context.window_manager
- msg = "New image created with measures. Open it in UV/image editor"
- camera_msg = "Unable to render. No camera found"
-
- # -----------------------------
- # Check camera
- # -----------------------------
- if scene.camera is None:
- self.report({'ERROR'}, camera_msg)
- return {'FINISHED'}
-
- objlist = self.draw_gl(context)
-
- # -----------------------------
- # Use current rendered image
- # -----------------------------
- if wm.archipack.render_type == "1":
- # noinspection PyBroadException
- try:
- result = bpy.data.images['Render Result']
- if result.has_data is False:
- bpy.ops.render.render()
- except:
- bpy.ops.render.render()
-
- print("Archipack: Using current render image on buffer")
- if self.render_main(context, objlist) is True:
- self.report({'INFO'}, msg)
-
- # -----------------------------
- # OpenGL image
- # -----------------------------
- elif wm.archipack.render_type == "2":
- self.set_camera_view()
- self.set_only_render(True)
-
- print("Archipack: Rendering opengl image")
- bpy.ops.render.opengl()
- if self.render_main(context, objlist) is True:
- self.report({'INFO'}, msg)
-
- self.set_only_render(False)
-
- # -----------------------------
- # OpenGL Animation
- # -----------------------------
- elif wm.archipack.render_type == "3":
- oldframe = scene.frame_current
- self.set_camera_view()
- self.set_only_render(True)
- flag = False
- # loop frames
- for frm in range(scene.frame_start, scene.frame_end + 1):
- scene.frame_set(frm)
- print("Archipack: Rendering opengl frame %04d" % frm)
- bpy.ops.render.opengl()
- flag = self.render_main(context, objlist, True)
- if flag is False:
- break
-
- self.set_only_render(False)
- scene.frame_current = oldframe
- if flag is True:
- self.report({'INFO'}, msg)
-
- # -----------------------------
- # Image
- # -----------------------------
- elif wm.archipack.render_type == "4":
- print("Archipack: Rendering image")
- bpy.ops.render.render()
- if self.render_main(context, objlist) is True:
- self.report({'INFO'}, msg)
-
- # -----------------------------
- # Animation
- # -----------------------------
- elif wm.archipack.render_type == "5":
- oldframe = scene.frame_current
- flag = False
- # loop frames
- for frm in range(scene.frame_start, scene.frame_end + 1):
- scene.frame_set(frm)
- print("Archipack: Rendering frame %04d" % frm)
- bpy.ops.render.render()
- flag = self.render_main(context, objlist, True)
- if flag is False:
- break
-
- scene.frame_current = oldframe
- if flag is True:
- self.report({'INFO'}, msg)
-
- self.hide_gl(context, objlist)
-
- return {'FINISHED'}
-
- # ---------------------
- # Set cameraView
- # ---------------------
- # noinspection PyMethodMayBeStatic
- def set_camera_view(self):
- for area in bpy.context.screen.areas:
- if area.type == 'VIEW_3D':
- area.spaces[0].region_3d.view_perspective = 'CAMERA'
-
- # -------------------------------------
- # Set only render status
- # -------------------------------------
- # noinspection PyMethodMayBeStatic
- def set_only_render(self, status):
- screen = bpy.context.screen
-
- v3d = False
- s = None
- # get spaceview_3d in current screen
- for a in screen.areas:
- if a.type == 'VIEW_3D':
- for s in a.spaces:
- if s.type == 'VIEW_3D':
- v3d = s
- break
-
- if v3d is not False:
- s.show_only_render = status
-
-
def register():
- bpy.utils.register_class(ARCHIPACK_OT_render)
bpy.utils.register_class(ARCHIPACK_OT_render_thumbs)
def unregister():
- bpy.utils.unregister_class(ARCHIPACK_OT_render)
bpy.utils.unregister_class(ARCHIPACK_OT_render_thumbs)
diff --git a/archipack/archipack_roof.py b/archipack/archipack_roof.py
index 7d396d36..5ab21a38 100644
--- a/archipack/archipack_roof.py
+++ b/archipack/archipack_roof.py
@@ -1564,7 +1564,7 @@ class RoofGenerator(CutAbleGenerator):
use_dissolve_boundaries=False,
verts=bm.verts,
edges=bm.edges,
- delimit=1)
+ delimit={'MATERIAL'})
geom = bm.faces[:]
verts = bm.verts[:]
@@ -1595,7 +1595,7 @@ class RoofGenerator(CutAbleGenerator):
BEVEL_AMT_PERCENT
};
"""
- offset_type = 3
+ offset_type = 'PERCENT'
if d.tile_offset > 0:
offset = - d.tile_offset / 100
@@ -1694,8 +1694,8 @@ class RoofGenerator(CutAbleGenerator):
step = 100 / ttl
- if d.quick_edit:
- context.scene.archipack_progress_text = "Build tiles:"
+ # if d.quick_edit:
+ # context.scene.archipack_progress_text = "Build tiles:"
for i, pan in enumerate(self.pans):
@@ -1742,8 +1742,8 @@ class RoofGenerator(CutAbleGenerator):
progress = step * i + substep * k
# print("progress %s" % (progress))
- if d.quick_edit:
- context.scene.archipack_progress = progress
+ # if d.quick_edit:
+ # context.scene.archipack_progress = progress
y = k * dy
@@ -1759,7 +1759,7 @@ class RoofGenerator(CutAbleGenerator):
for j in range(nx):
x = x0 + j * dx
- lM = tM * Matrix([
+ lM = tM @ Matrix([
[sx, 0, 0, x],
[0, sy, 0, -y],
[0, 0, sz, 0],
@@ -1768,7 +1768,7 @@ class RoofGenerator(CutAbleGenerator):
v = len(verts)
- verts.extend([lM * p for p in t_pts])
+ verts.extend([lM @ p for p in t_pts])
faces.extend([tuple(i + v for i in f) for f in t_faces])
mid = randint(idmat, idmat + rand)
t_mats = [mid for i in range(n_faces)]
@@ -1847,7 +1847,7 @@ class RoofGenerator(CutAbleGenerator):
segs[-1].p1 = p
f_geom = [f for f in bm.faces if not pan.inside(f.calc_center_median().to_2d(), segs)]
if len(f_geom) > 0:
- bmesh.ops.delete(bm, geom=f_geom, context=5)
+ bmesh.ops.delete(bm, geom=f_geom, context="FACES")
self.cut_holes(bm, pan)
@@ -1856,7 +1856,7 @@ class RoofGenerator(CutAbleGenerator):
use_dissolve_boundaries=False,
verts=bm.verts[:],
edges=bm.edges[:],
- delimit=1)
+ delimit={'MATERIAL'})
if d.tile_bevel:
geom = bm.verts[:]
@@ -1868,7 +1868,7 @@ class RoofGenerator(CutAbleGenerator):
segments=d.tile_bevel_segs,
profile=0.5,
vertex_only=False,
- clight_overlap=True,
+ clamp_overlap=True,
material=-1)
if d.tile_solidify:
@@ -1881,8 +1881,8 @@ class RoofGenerator(CutAbleGenerator):
bmed.bmesh_join(context, o, [bm], normal_update=True)
bpy.ops.object.mode_set(mode='OBJECT')
- if d.quick_edit:
- context.scene.archipack_progress = -1
+ # if d.quick_edit:
+ # context.scene.archipack_progress = -1
def _bargeboard(self, s, i, boundary, pan,
width, height, altitude, offset, idmat,
@@ -2774,7 +2774,7 @@ class RoofGenerator(CutAbleGenerator):
use_dissolve_boundaries=False,
verts=bm.verts,
edges=bm.edges,
- delimit=1)
+ delimit={'MATERIAL'})
geom = bm.faces[:]
verts = bm.verts[:]
@@ -3040,7 +3040,7 @@ class RoofGenerator(CutAbleGenerator):
t_verts[i].z += dz * t_verts[i].y
for k in range(n_x):
- lM = tM * Matrix([
+ lM = tM @ Matrix([
[1, 0, 0, x0 + k * dx],
[0, -1, 0, 0],
[0, 0, 1, 0],
@@ -3048,7 +3048,7 @@ class RoofGenerator(CutAbleGenerator):
])
f = len(verts)
- verts.extend([lM * p for p in t_verts])
+ verts.extend([lM @ p for p in t_verts])
faces.extend([tuple(i + f for i in p) for p in t_faces])
matids.extend(t_idmats)
uvs.extend(t_uvs)
@@ -3132,14 +3132,14 @@ class RoofGenerator(CutAbleGenerator):
t_verts[i].z -= t_verts[i].y * (pan.slope - d.tile_size_z / d.tile_size_y)
for k in range(n_obj):
- lM = tM * Matrix([
+ lM = tM @ Matrix([
[1, 0, 0, x0 + k * dx],
[0, -1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]
])
v = len(verts)
- verts.extend([lM * p for p in t_verts])
+ verts.extend([lM @ p for p in t_verts])
faces.extend([tuple(i + v for i in f) for f in t_faces])
matids.extend(t_idmats)
uvs.extend(t_uvs)
@@ -3243,19 +3243,19 @@ class RoofGenerator(CutAbleGenerator):
pts = [p.to_3d() for p in pts]
if hole_obj is None:
- context.scene.objects.active = o.parent
+ context.view_layer.objects.active = o.parent
bpy.ops.archipack.roof_cutter(parent=d.t_parent, auto_manipulate=False)
hole_obj = context.active_object
else:
- context.scene.objects.active = hole_obj
+ context.view_layer.objects.active = hole_obj
- hole_obj.select = True
+ hole_obj.select_set(state=True)
if d.parts[0].a0 < 0:
y = -d.t_dist_y
else:
y = d.t_dist_y
- hole_obj.matrix_world = o.matrix_world * Matrix([
+ hole_obj.matrix_world = o.matrix_world @ Matrix([
[1, 0, 0, 0],
[0, 1, 0, y],
[0, 0, 1, 0],
@@ -3265,15 +3265,15 @@ class RoofGenerator(CutAbleGenerator):
hd = archipack_roof_cutter.datablock(hole_obj)
hd.boundary = o.name
hd.update_points(context, hole_obj, pts, update_parent=update_parent)
- hole_obj.select = False
+ hole_obj.select_set(state=False)
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
def change_coordsys(self, fromTM, toTM):
"""
move shape fromTM into toTM coordsys
"""
- dp = (toTM.inverted() * fromTM.translation).to_2d()
+ dp = (toTM.inverted() @ fromTM.translation).to_2d()
da = toTM.row[1].to_2d().angle_signed(fromTM.row[1].to_2d())
ca = cos(da)
sa = sin(da)
@@ -3282,7 +3282,7 @@ class RoofGenerator(CutAbleGenerator):
[sa, ca]
])
for s in self.segs:
- tp = (rM * s.p0) - s.p0 + dp
+ tp = (rM @ s.p0) - s.p0 + dp
s.rotate(da)
s.translate(tp)
@@ -3357,9 +3357,9 @@ class RoofGenerator(CutAbleGenerator):
wall_t[widx].append((0, z, 0))
old = context.active_object
- old_sel = wall.select
- wall.select = True
- context.scene.objects.active = wall
+ old_sel = wall.select_get()
+ wall.select_set(state=True)
+ context.view_layer.objects.active = wall
wd.auto_update = False
# setup splits count and first split to 0
@@ -3412,8 +3412,8 @@ class RoofGenerator(CutAbleGenerator):
for s in wg.segs:
s.as_curve(context)
"""
- wall.select = old_sel
- context.scene.objects.active = old
+ wall.select_set(state=old_sel)
+ context.view_layer.objects.active = old
def boundary(self, context, o):
"""
@@ -3494,14 +3494,14 @@ def update_components(self, context):
class ArchipackSegment():
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
max=1000.0,
default=4.0,
update=update
)
- a0 = FloatProperty(
+ a0 : FloatProperty(
name="Angle",
min=-2 * pi,
max=2 * pi,
@@ -3509,17 +3509,17 @@ class ArchipackSegment():
subtype='ANGLE', unit='ROTATION',
update=update_cutter
)
- manipulators = CollectionProperty(type=archipack_manipulator)
+ manipulators : CollectionProperty(type=archipack_manipulator)
class ArchipackLines():
- n_parts = IntProperty(
+ n_parts : IntProperty(
name="Parts",
min=1,
default=1, update=update_manipulators
)
# UI layout related
- parts_expand = BoolProperty(
+ parts_expand : BoolProperty(
default=False
)
@@ -3580,37 +3580,37 @@ class ArchipackLines():
class archipack_roof_segment(ArchipackSegment, PropertyGroup):
- bound_idx = IntProperty(
+ bound_idx : IntProperty(
name="Link to",
default=0,
min=0,
update=update_manipulators
)
- width_left = FloatProperty(
+ width_left : FloatProperty(
name="L Width",
min=0.01,
default=3.0,
update=update_cutter
)
- width_right = FloatProperty(
+ width_right : FloatProperty(
name="R Width",
min=0.01,
default=3.0,
update=update_cutter
)
- slope_left = FloatProperty(
+ slope_left : FloatProperty(
name="L slope",
min=0.0,
default=0.3,
update=update_cutter
)
- slope_right = FloatProperty(
+ slope_right : FloatProperty(
name="R slope",
min=0.0,
default=0.3,
update=update_cutter
)
- auto_left = EnumProperty(
+ auto_left : EnumProperty(
description="Left mode",
name="Left",
items=(
@@ -3622,7 +3622,7 @@ class archipack_roof_segment(ArchipackSegment, PropertyGroup):
default="AUTO",
update=update_manipulators
)
- auto_right = EnumProperty(
+ auto_right : EnumProperty(
description="Right mode",
name="Right",
items=(
@@ -3634,19 +3634,19 @@ class archipack_roof_segment(ArchipackSegment, PropertyGroup):
default="AUTO",
update=update_manipulators
)
- triangular_end = BoolProperty(
+ triangular_end : BoolProperty(
name="Triangular end",
default=False,
update=update
)
- take_precedence = BoolProperty(
+ take_precedence : BoolProperty(
name="Take precedence",
description="On T segment take width precedence",
default=False,
update=update
)
- constraint_type = EnumProperty(
+ constraint_type : EnumProperty(
items=(
('HORIZONTAL', 'Horizontal', '', 0),
('SLOPE', 'Slope', '', 1)
@@ -3655,7 +3655,7 @@ class archipack_roof_segment(ArchipackSegment, PropertyGroup):
update=update_manipulators
)
- enforce_part = EnumProperty(
+ enforce_part : EnumProperty(
name="Enforce part",
items=(
('AUTO', 'Auto', '', 0),
@@ -3687,7 +3687,7 @@ class archipack_roof_segment(ArchipackSegment, PropertyGroup):
if self.constraint_type == 'SLOPE':
box.prop(self, "enforce_part", text="")
else:
- box.label("Part 1:")
+ box.label(text="Part 1:")
box.prop(self, "length")
box.prop(self, "a0")
@@ -3720,63 +3720,63 @@ class archipack_roof_segment(ArchipackSegment, PropertyGroup):
class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup):
- parts = CollectionProperty(type=archipack_roof_segment)
- z = FloatProperty(
+ parts : CollectionProperty(type=archipack_roof_segment)
+ z : FloatProperty(
name="Altitude",
default=3, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update_childs
)
- slope_left = FloatProperty(
+ slope_left : FloatProperty(
name="L slope",
default=0.5, precision=2, step=1,
update=update_childs
)
- slope_right = FloatProperty(
+ slope_right : FloatProperty(
name="R slope",
default=0.5, precision=2, step=1,
update=update_childs
)
- width_left = FloatProperty(
+ width_left : FloatProperty(
name="L width",
default=3, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update_cutter
)
- width_right = FloatProperty(
+ width_right : FloatProperty(
name="R width",
default=3, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update_cutter
)
- draft = BoolProperty(
+ draft : BoolProperty(
options={'SKIP_SAVE'},
name="Draft mode",
default=False,
update=update_manipulators
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
)
- quick_edit = BoolProperty(
+ quick_edit : BoolProperty(
options={'SKIP_SAVE'},
name="Quick Edit",
- default=True
+ default=False
)
- tile_enable = BoolProperty(
+ tile_enable : BoolProperty(
name="Enable",
default=True,
update=update_components
)
- tile_solidify = BoolProperty(
+ tile_solidify : BoolProperty(
name="Solidify",
default=True,
update=update_components
)
- tile_height = FloatProperty(
+ tile_height : FloatProperty(
name="Height",
description="Amount for solidify",
min=0,
@@ -3784,12 +3784,12 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_bevel = BoolProperty(
+ tile_bevel : BoolProperty(
name="Bevel",
default=False,
update=update_components
)
- tile_bevel_amt = FloatProperty(
+ tile_bevel_amt : FloatProperty(
name="Amount",
description="Amount for bevel",
min=0,
@@ -3797,19 +3797,19 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_bevel_segs = IntProperty(
+ tile_bevel_segs : IntProperty(
name="Segs",
description="Bevel Segs",
min=1,
default=2,
update=update_components
)
- tile_alternate = BoolProperty(
+ tile_alternate : BoolProperty(
name="Alternate",
default=False,
update=update_components
)
- tile_offset = FloatProperty(
+ tile_offset : FloatProperty(
name="Offset",
description="Offset from start",
min=0,
@@ -3817,14 +3817,14 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
subtype="PERCENTAGE",
update=update_components
)
- tile_altitude = FloatProperty(
+ tile_altitude : FloatProperty(
name="Altitude",
description="Altitude from roof",
default=0.1,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_size_x = FloatProperty(
+ tile_size_x : FloatProperty(
name="Width",
description="Size of tiles on x axis",
min=0.01,
@@ -3832,7 +3832,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_size_y = FloatProperty(
+ tile_size_y : FloatProperty(
name="Length",
description="Size of tiles on y axis",
min=0.01,
@@ -3840,7 +3840,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_size_z = FloatProperty(
+ tile_size_z : FloatProperty(
name="Thickness",
description="Size of tiles on z axis",
min=0.0,
@@ -3848,7 +3848,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_space_x = FloatProperty(
+ tile_space_x : FloatProperty(
name="Width",
description="Space between tiles on x axis",
min=0.01,
@@ -3856,7 +3856,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_space_y = FloatProperty(
+ tile_space_y : FloatProperty(
name="Length",
description="Space between tiles on y axis",
min=0.01,
@@ -3864,25 +3864,25 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_fit_x = BoolProperty(
+ tile_fit_x : BoolProperty(
name="Fit x",
description="Fit roof on x axis",
default=True,
update=update_components
)
- tile_fit_y = BoolProperty(
+ tile_fit_y : BoolProperty(
name="Fit y",
description="Fit roof on y axis",
default=True,
update=update_components
)
- tile_expand = BoolProperty(
+ tile_expand : BoolProperty(
options={'SKIP_SAVE'},
name="Tiles",
description="Expand tiles panel",
default=False
)
- tile_model = EnumProperty(
+ tile_model : EnumProperty(
name="Model",
items=(
('BRAAS1', 'Braas 1', '', 0),
@@ -3899,14 +3899,14 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
default="BRAAS2",
update=update_components
)
- tile_side = FloatProperty(
+ tile_side : FloatProperty(
name="Side",
description="Space on side",
default=0,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_couloir = FloatProperty(
+ tile_couloir : FloatProperty(
name="Valley",
description="Space between tiles on valley",
min=0,
@@ -3914,7 +3914,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- tile_border = FloatProperty(
+ tile_border : FloatProperty(
name="Bottom",
description="Tiles offset from bottom",
default=0,
@@ -3922,25 +3922,25 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
update=update_components
)
- gutter_expand = BoolProperty(
+ gutter_expand : BoolProperty(
options={'SKIP_SAVE'},
name="Gutter",
description="Expand gutter panel",
default=False
)
- gutter_enable = BoolProperty(
+ gutter_enable : BoolProperty(
name="Enable",
default=True,
update=update_components
)
- gutter_alt = FloatProperty(
+ gutter_alt : FloatProperty(
name="Altitude",
description="altitude",
default=0,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- gutter_width = FloatProperty(
+ gutter_width : FloatProperty(
name="Width",
description="Width",
min=0.01,
@@ -3948,7 +3948,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- gutter_dist = FloatProperty(
+ gutter_dist : FloatProperty(
name="Spacing",
description="Spacing",
min=0,
@@ -3956,7 +3956,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- gutter_boudin = FloatProperty(
+ gutter_boudin : FloatProperty(
name="Small width",
description="Small width",
min=0,
@@ -3964,25 +3964,25 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- gutter_segs = IntProperty(
+ gutter_segs : IntProperty(
default=6,
min=1,
name="Segs",
update=update_components
)
- beam_expand = BoolProperty(
+ beam_expand : BoolProperty(
options={'SKIP_SAVE'},
name="Beam",
description="Expand beam panel",
default=False
)
- beam_enable = BoolProperty(
+ beam_enable : BoolProperty(
name="Ridge pole",
default=True,
update=update_components
)
- beam_width = FloatProperty(
+ beam_width : FloatProperty(
name="Width",
description="Width",
min=0.01,
@@ -3990,7 +3990,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- beam_height = FloatProperty(
+ beam_height : FloatProperty(
name="Height",
description="Height",
min=0.01,
@@ -3998,26 +3998,26 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- beam_offset = FloatProperty(
+ beam_offset : FloatProperty(
name="Offset",
description="Distance from roof border",
default=0.02,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- beam_alt = FloatProperty(
+ beam_alt : FloatProperty(
name="Altitude",
description="Altitude from roof",
default=-0.15,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- beam_sec_enable = BoolProperty(
+ beam_sec_enable : BoolProperty(
name="Hip rafter",
default=True,
update=update_components
)
- beam_sec_width = FloatProperty(
+ beam_sec_width : FloatProperty(
name="Width",
description="Width",
min=0.01,
@@ -4025,7 +4025,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- beam_sec_height = FloatProperty(
+ beam_sec_height : FloatProperty(
name="Height",
description="Height",
min=0.01,
@@ -4033,19 +4033,19 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- beam_sec_alt = FloatProperty(
+ beam_sec_alt : FloatProperty(
name="Altitude",
description="Distance from roof",
default=-0.1,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- rafter_enable = BoolProperty(
+ rafter_enable : BoolProperty(
name="Rafter",
default=True,
update=update_components
)
- rafter_width = FloatProperty(
+ rafter_width : FloatProperty(
name="Width",
description="Width",
min=0.01,
@@ -4053,7 +4053,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- rafter_height = FloatProperty(
+ rafter_height : FloatProperty(
name="Height",
description="Height",
min=0.01,
@@ -4061,7 +4061,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- rafter_spacing = FloatProperty(
+ rafter_spacing : FloatProperty(
name="Spacing",
description="Spacing",
min=0.1,
@@ -4069,7 +4069,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- rafter_start = FloatProperty(
+ rafter_start : FloatProperty(
name="Offset",
description="Spacing from roof border",
min=0,
@@ -4077,7 +4077,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- rafter_alt = FloatProperty(
+ rafter_alt : FloatProperty(
name="Altitude",
description="Altitude from roof",
max=-0.0001,
@@ -4086,25 +4086,25 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
update=update_components
)
- hip_enable = BoolProperty(
+ hip_enable : BoolProperty(
name="Enable",
default=True,
update=update_components
)
- hip_expand = BoolProperty(
+ hip_expand : BoolProperty(
options={'SKIP_SAVE'},
name="Hips",
description="Expand hips panel",
default=False
)
- hip_alt = FloatProperty(
+ hip_alt : FloatProperty(
name="Altitude",
description="Hip altitude from roof",
default=0.1,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- hip_space_x = FloatProperty(
+ hip_space_x : FloatProperty(
name="Spacing",
description="Space between hips",
min=0.01,
@@ -4112,7 +4112,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- hip_size_x = FloatProperty(
+ hip_size_x : FloatProperty(
name="Length",
description="Length of hip",
min=0.01,
@@ -4120,7 +4120,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- hip_size_y = FloatProperty(
+ hip_size_y : FloatProperty(
name="Width",
description="Width of hip",
min=0.01,
@@ -4128,7 +4128,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- hip_size_z = FloatProperty(
+ hip_size_z : FloatProperty(
name="Height",
description="Height of hip",
min=0.0,
@@ -4136,7 +4136,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- hip_model = EnumProperty(
+ hip_model : EnumProperty(
name="Model",
items=(
('ROUND', 'Round', '', 0),
@@ -4146,32 +4146,32 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
default="ROUND",
update=update_components
)
- valley_altitude = FloatProperty(
+ valley_altitude : FloatProperty(
name="Altitude",
description="Valley altitude from roof",
default=0.1,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- valley_enable = BoolProperty(
+ valley_enable : BoolProperty(
name="Valley",
default=True,
update=update_components
)
- fascia_enable = BoolProperty(
+ fascia_enable : BoolProperty(
name="Enable",
description="Enable Fascia",
default=True,
update=update_components
)
- fascia_expand = BoolProperty(
+ fascia_expand : BoolProperty(
options={'SKIP_SAVE'},
name="Fascia",
description="Expand fascia panel",
default=False
)
- fascia_height = FloatProperty(
+ fascia_height : FloatProperty(
name="Height",
description="Height",
min=0.01,
@@ -4179,7 +4179,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- fascia_width = FloatProperty(
+ fascia_width : FloatProperty(
name="Width",
description="Width",
min=0.01,
@@ -4187,14 +4187,14 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- fascia_offset = FloatProperty(
+ fascia_offset : FloatProperty(
name="Offset",
description="Offset from roof border",
default=0,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- fascia_altitude = FloatProperty(
+ fascia_altitude : FloatProperty(
name="Altitude",
description="Fascia altitude from roof",
default=0.1,
@@ -4202,19 +4202,19 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
update=update_components
)
- bargeboard_enable = BoolProperty(
+ bargeboard_enable : BoolProperty(
name="Enable",
description="Enable Bargeboard",
default=True,
update=update_components
)
- bargeboard_expand = BoolProperty(
+ bargeboard_expand : BoolProperty(
options={'SKIP_SAVE'},
name="Bargeboard",
description="Expand Bargeboard panel",
default=False
)
- bargeboard_height = FloatProperty(
+ bargeboard_height : FloatProperty(
name="Height",
description="Height",
min=0.01,
@@ -4222,7 +4222,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- bargeboard_width = FloatProperty(
+ bargeboard_width : FloatProperty(
name="Width",
description="Width",
min=0.01,
@@ -4230,14 +4230,14 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- bargeboard_offset = FloatProperty(
+ bargeboard_offset : FloatProperty(
name="Offset",
description="Offset from roof border",
default=0.001,
unit='LENGTH', subtype='DISTANCE',
update=update_components
)
- bargeboard_altitude = FloatProperty(
+ bargeboard_altitude : FloatProperty(
name="Altitude",
description="Fascia altitude from roof",
default=0.1,
@@ -4245,25 +4245,25 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
update=update_components
)
- t_parent = StringProperty(
+ t_parent : StringProperty(
name="Parent",
default="",
update=update_parent
)
- t_part = IntProperty(
+ t_part : IntProperty(
name="Part",
description="Parent part index",
default=0,
min=0,
update=update_cutter
)
- t_dist_x = FloatProperty(
+ t_dist_x : FloatProperty(
name="Dist x",
description="Location on axis ",
default=0,
update=update_cutter
)
- t_dist_y = FloatProperty(
+ t_dist_y : FloatProperty(
name="Dist y",
description="Lateral distance from axis",
min=0.0001,
@@ -4271,21 +4271,21 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
update=update_cutter
)
- hole_offset_left = FloatProperty(
+ hole_offset_left : FloatProperty(
name="Left",
description="Left distance from border",
min=0,
default=0,
update=update_cutter
)
- hole_offset_right = FloatProperty(
+ hole_offset_right : FloatProperty(
name="Right",
description="Right distance from border",
min=0,
default=0,
update=update_cutter
)
- hole_offset_front = FloatProperty(
+ hole_offset_front : FloatProperty(
name="Front",
description="Front distance from border",
default=0,
@@ -4420,7 +4420,7 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
t = (d.t_dist_x / seg.length)
x, y, z = seg.lerp(t).to_3d()
dy = -seg.v.normalized()
- child.matrix_world = o.matrix_world * Matrix([
+ child.matrix_world = o.matrix_world @ Matrix([
[dy.x, -dy.y, 0, x],
[dy.y, dy.x, 0, y],
[0, 0, 1, z],
@@ -4438,13 +4438,13 @@ class archipack_roof(ArchipackLines, ArchipackObject, Manipulable, PropertyGroup
d = archipack_roof.datablock(child)
if d is not None and d.t_parent == o.name:
# print("upate_childs(%s)" % (child.name))
- child.select = True
- context.scene.objects.active = child
+ child.select_set(state=True)
+ context.view_layer.objects.active = child
# regenerate hole
d.update(context, update_hole=True, update_parent=False)
- child.select = False
- o.select = True
- context.scene.objects.active = o
+ child.select_set(state=False)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
def update(self,
context,
@@ -4726,8 +4726,8 @@ def update_operation(self, context):
class archipack_roof_cutter_segment(ArchipackCutterPart, PropertyGroup):
- manipulators = CollectionProperty(type=archipack_manipulator)
- type = EnumProperty(
+ manipulators : CollectionProperty(type=archipack_manipulator)
+ type : EnumProperty(
name="Type",
items=(
('SIDE', 'Side', 'Side with bargeboard', 0),
@@ -4754,8 +4754,8 @@ class archipack_roof_cutter_segment(ArchipackCutterPart, PropertyGroup):
class archipack_roof_cutter(ArchipackCutter, ArchipackObject, Manipulable, PropertyGroup):
# boundary
- parts = CollectionProperty(type=archipack_roof_cutter_segment)
- boundary = StringProperty(
+ parts : CollectionProperty(type=archipack_roof_cutter_segment)
+ boundary : StringProperty(
default="",
name="Boundary",
description="Boundary of t child to cut parent"
@@ -4778,11 +4778,11 @@ class archipack_roof_cutter(ArchipackCutter, ArchipackObject, Manipulable, Prope
d = archipack_roof.datablock(o.parent)
if d is not None:
- o.parent.select = True
- context.scene.objects.active = o.parent
+ o.parent.select_set(state=True)
+ context.view_layer.objects.active = o.parent
d.update(context, update_childs=False, update_hole=False)
- o.parent.select = False
- context.scene.objects.active = o
+ o.parent.select_set(state=False)
+ context.view_layer.objects.active = o
# print("update_parent")
@@ -4791,7 +4791,7 @@ class ARCHIPACK_PT_roof_cutter(Panel):
bl_label = "Roof Cutter"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -4808,7 +4808,7 @@ class ARCHIPACK_PT_roof_cutter(Panel):
box.label(text="Auto Cutter:")
box.label(text=prop.boundary)
else:
- box.operator('archipack.roof_cutter_manipulate', icon='HAND')
+ box.operator('archipack.roof_cutter_manipulate', icon='VIEW_PAN')
box.prop(prop, 'operation', text="")
box = layout.box()
box.label(text="From curve")
@@ -4828,7 +4828,7 @@ class ARCHIPACK_PT_roof(Panel):
bl_label = "Roof"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -4842,13 +4842,13 @@ class ARCHIPACK_PT_roof(Panel):
scene = context.scene
layout = self.layout
row = layout.row(align=True)
- row.operator('archipack.roof_manipulate', icon='HAND')
+ row.operator('archipack.roof_manipulate', icon='VIEW_PAN')
box = layout.box()
row = box.row(align=True)
row.operator("archipack.roof_preset_menu", text=bpy.types.ARCHIPACK_OT_roof_preset_menu.bl_label)
- row.operator("archipack.roof_preset", text="", icon='ZOOMIN')
- row.operator("archipack.roof_preset", text="", icon='ZOOMOUT').remove_active = True
+ row.operator("archipack.roof_preset", text="", icon='ADD')
+ row.operator("archipack.roof_preset", text="", icon='REMOVE').remove_active = True
box = layout.box()
box.prop_search(prop, "t_parent", scene, "objects", text="Parent", icon='OBJECT_DATA')
layout.operator('archipack.roof_cutter').parent = o.name
@@ -5029,9 +5029,9 @@ class ARCHIPACK_OT_roof(ArchipackCreateTool, Operator):
d = m.archipack_roof.add()
# make manipulators selectable
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.add_material(o)
# disable progress bar when
@@ -5050,8 +5050,8 @@ class ARCHIPACK_OT_roof(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
@@ -5066,7 +5066,7 @@ class ARCHIPACK_OT_roof_cutter(ArchipackCreateTool, Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- parent = StringProperty("")
+ parent : StringProperty("")
def create(self, context):
m = bpy.data.meshes.new("Roof Cutter")
@@ -5081,7 +5081,7 @@ class ARCHIPACK_OT_roof_cutter(ArchipackCreateTool, Operator):
x1, y1, z = bbox[6]
x = 0.2 * (x1 - x0)
y = 0.2 * (y1 - y0)
- o.matrix_world = parent.matrix_world * Matrix([
+ o.matrix_world = parent.matrix_world @ Matrix([
[1, 0, 0, -3 * x],
[0, 1, 0, 0],
[0, 0, 1, 0],
@@ -5104,9 +5104,9 @@ class ARCHIPACK_OT_roof_cutter(ArchipackCreateTool, Operator):
o.location = context.scene.cursor_location
# make manipulators selectable
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.add_material(o)
self.load_preset(d)
update_operation(d, context)
@@ -5119,8 +5119,8 @@ class ARCHIPACK_OT_roof_cutter(ArchipackCreateTool, Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
@@ -5140,7 +5140,7 @@ class ARCHIPACK_OT_roof_from_curve(Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- auto_manipulate = BoolProperty(default=True)
+ auto_manipulate : BoolProperty(default=True)
@classmethod
def poll(self, context):
@@ -5149,7 +5149,7 @@ class ARCHIPACK_OT_roof_from_curve(Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
curve = context.active_object
@@ -5159,9 +5159,9 @@ class ARCHIPACK_OT_roof_from_curve(Operator):
# make manipulators selectable
d.manipulable_selectable = True
d.user_defined_path = curve.name
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
d.update_path(context)
spline = curve.data.splines[0]
@@ -5172,14 +5172,14 @@ class ARCHIPACK_OT_roof_from_curve(Operator):
else:
pt = Vector((0, 0, 0))
# pretranslate
- o.matrix_world = curve.matrix_world * Matrix([
+ o.matrix_world = curve.matrix_world @ Matrix([
[1, 0, 0, pt.x],
[0, 1, 0, pt.y],
[0, 0, 1, pt.z],
[0, 0, 0, 1]
])
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return o
# -----------------------------------------------------
@@ -5250,7 +5250,7 @@ class ArchipackThrottleHandler():
def start_timer(self, context):
self.start = time.time()
- self._timer = context.window_manager.event_timer_add(self.delay, context.window)
+ self._timer = context.window_manager.event_timer_add(self.delay, window=context.window)
def stop_timer(self, context):
if self._timer is not None:
@@ -5300,7 +5300,7 @@ class ARCHIPACK_OT_roof_throttle_update(Operator):
bl_idname = "archipack.roof_throttle_update"
bl_label = "Update childs with a delay"
- name = StringProperty()
+ name : StringProperty()
def kill_handler(self, context, name):
if name in throttle_handlers.keys():
@@ -5321,16 +5321,16 @@ class ARCHIPACK_OT_roof_throttle_update(Operator):
o = context.scene.objects.get(self.name)
# print("delay update of %s" % (self.name))
if o is not None:
- selected = o.select
- o.select = True
- context.scene.objects.active = o
+ selected = o.select_get()
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
d = o.data.archipack_roof[0]
d.update(context,
force_update=True,
update_parent=False)
# skip_parent_update=self.skip_parent_update)
- o.select = selected
- context.scene.objects.active = act
+ o.select_set(state=selected)
+ context.view_layer.objects.active = act
del throttle_handlers[self.name]
return {'FINISHED'}
else:
diff --git a/archipack/archipack_slab.py b/archipack/archipack_slab.py
index a6cc9bf6..f4112b08 100644
--- a/archipack/archipack_slab.py
+++ b/archipack/archipack_slab.py
@@ -220,7 +220,7 @@ class SlabGenerator(CutAblePolygon, CutAbleGenerator):
# rotate seg
seg.rotate(a)
# rotate delta from rotation center to segment start
- dp = rM * (seg.p0 - p0)
+ dp = rM @ (seg.p0 - p0)
seg.translate(dp)
def translate(self, idx_from, dp):
@@ -319,7 +319,7 @@ materials_enum = (
class archipack_slab_material(PropertyGroup):
- index = EnumProperty(
+ index : EnumProperty(
items=materials_enum,
default='4',
update=update
@@ -349,8 +349,8 @@ class archipack_slab_child(PropertyGroup):
"""
Store child fences to be able to sync
"""
- child_name = StringProperty()
- idx = IntProperty()
+ child_name : StringProperty()
+ idx : IntProperty()
def get_child(self, context):
d = None
@@ -439,7 +439,7 @@ class ArchipackSegment():
@TODO: share this base class with
stair, wall, fence, slab
"""
- type = EnumProperty(
+ type : EnumProperty(
items=(
('S_SEG', 'Straight', '', 0),
('C_SEG', 'Curved', '', 1),
@@ -447,19 +447,19 @@ class ArchipackSegment():
default='S_SEG',
update=update_type
)
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
default=2.0,
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.5,
default=0.7,
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -467,7 +467,7 @@ class ArchipackSegment():
subtype='ANGLE', unit='ROTATION',
update=update
)
- a0 = FloatProperty(
+ a0 : FloatProperty(
name="Start angle",
min=-2 * pi,
max=2 * pi,
@@ -475,21 +475,21 @@ class ArchipackSegment():
subtype='ANGLE', unit='ROTATION',
update=update
)
- offset = FloatProperty(
+ offset : FloatProperty(
name="Offset",
description="Add to current segment offset",
default=0,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- linked_idx = IntProperty(default=-1)
+ linked_idx : IntProperty(default=-1)
# @TODO:
# flag to handle wall's x_offset
# when set add wall offset value to segment offset
# pay attention at allowing per wall segment offset
- manipulators = CollectionProperty(type=archipack_manipulator)
+ manipulators : CollectionProperty(type=archipack_manipulator)
def find_in_selection(self, context):
raise NotImplementedError
@@ -543,38 +543,38 @@ class archipack_slab_part(ArchipackSegment, PropertyGroup):
class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
# boundary
- n_parts = IntProperty(
+ n_parts : IntProperty(
name="Parts",
min=1,
default=1, update=update_manipulators
)
- parts = CollectionProperty(type=archipack_slab_part)
- closed = BoolProperty(
+ parts : CollectionProperty(type=archipack_slab_part)
+ closed : BoolProperty(
default=True,
name="Close",
options={'SKIP_SAVE'},
update=update_manipulators
)
# UI layout related
- parts_expand = BoolProperty(
+ parts_expand : BoolProperty(
options={'SKIP_SAVE'},
default=False
)
- x_offset = FloatProperty(
+ x_offset : FloatProperty(
name="Offset",
min=-1000, max=1000,
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- z = FloatProperty(
+ z : FloatProperty(
name="Thickness",
default=0.3, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- auto_synch = BoolProperty(
+ auto_synch : BoolProperty(
name="Auto-Synch",
description="Keep wall in synch when editing",
default=True,
@@ -590,7 +590,7 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
# .auto_update = False
# bulk changes
# .auto_update = True
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
@@ -696,17 +696,17 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
o = context.active_object
bpy.ops.archipack.fence(auto_manipulate=False)
c = context.active_object
- c.select = True
+ c.select_set(state=True)
c.data.archipack_fence[0].n_parts = 3
- c.select = False
+ c.select_set(state=False)
# link to o
c.location = Vector((0, 0, 0))
c.parent = o
c.location = g.segs[where + 1].p0.to_3d()
self.add_child(c.name, where + 1)
# c.matrix_world.translation = g.segs[where].p1.to_3d()
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.relocate_childs(context, o, g)
def add_part(self, context, length):
@@ -736,7 +736,7 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
dmax = 0.2
for c in o.children:
if (c.data and 'archipack_fence' in c.data):
- pt = (itM * c.matrix_world.translation).to_2d()
+ pt = (itM @ c.matrix_world.translation).to_2d()
for idx, seg in enumerate(g.segs):
# may be optimized with a bound check
res, d, t = seg.point_sur_segment(pt)
@@ -874,14 +874,14 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
else:
d.parts[i].length = max(0.01, seg.length)
- wall.select = True
- context.scene.objects.active = wall
+ wall.select_set(state=True)
+ context.view_layer.objects.active = wall
d.auto_update = True
- wall.select = False
+ wall.select_set(state=False)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
wall.matrix_world = o.matrix_world.copy()
@@ -897,11 +897,11 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
ca = cos(a)
if d is not None:
- c.select = True
+ c.select_set(state=True)
# auto_update need object to be active to
# setup manipulators on the right object
- context.scene.objects.active = c
+ context.view_layer.objects.active = c
d.auto_update = False
for i, part in enumerate(d.parts):
@@ -915,11 +915,11 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
part.radius = self.parts[i + child.idx].radius
d.parts[0].a0 = pi / 2
d.auto_update = True
- c.select = False
+ c.select_set(state=False)
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
# preTranslate
- c.matrix_world = tM * Matrix([
+ c.matrix_world = tM @ Matrix([
[sa, ca, 0, x],
[-ca, sa, 0, y],
[0, 0, 1, 0],
@@ -1034,18 +1034,18 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
# since this can lower points count by a resolution factor
# use normalized to handle non linear t
if resolution == 0:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
v = (p1.co - p0.co).normalized()
d1 = (p0.handle_right - p0.co).normalized()
d2 = (p1.co - p1.handle_left).normalized()
if d1 == v and d2 == v:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
- seg = interpolate_bezier(wM * p0.co,
- wM * p0.handle_right,
- wM * p1.handle_left,
- wM * p1.co,
+ seg = interpolate_bezier(wM @ p0.co,
+ wM @ p0.handle_right,
+ wM @ p1.handle_left,
+ wM @ p1.co,
resolution + 1)
for i in range(resolution):
pts.append(seg[i].to_3d())
@@ -1053,7 +1053,7 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
def from_spline(self, wM, resolution, spline):
pts = []
if spline.type == 'POLY':
- pts = [wM * p.co.to_3d() for p in spline.points]
+ pts = [wM @ p.co.to_3d() for p in spline.points]
if spline.use_cyclic_u:
pts.append(pts[0])
elif spline.type == 'BEZIER':
@@ -1068,7 +1068,7 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
self.interpolate_bezier(pts, wM, p0, p1, resolution)
pts.append(pts[0])
else:
- pts.append(wM * points[-1].co)
+ pts.append(wM @ points[-1].co)
self.from_points(pts, spline.use_cyclic_u)
@@ -1147,8 +1147,8 @@ class archipack_slab(ArchipackObject, Manipulable, PropertyGroup):
# relocate before cutting segs
self.relocate_childs(context, o, g)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
g.cut(context, o)
@@ -1244,8 +1244,8 @@ def update_operation(self, context):
class archipack_slab_cutter_segment(ArchipackCutterPart, PropertyGroup):
- manipulators = CollectionProperty(type=archipack_manipulator)
- type = EnumProperty(
+ manipulators : CollectionProperty(type=archipack_manipulator)
+ type : EnumProperty(
name="Type",
items=(
('DEFAULT', 'Side', 'Side with rake', 0),
@@ -1278,7 +1278,7 @@ class archipack_slab_cutter_segment(ArchipackCutterPart, PropertyGroup):
class archipack_slab_cutter(ArchipackCutter, ArchipackObject, Manipulable, PropertyGroup):
- parts = CollectionProperty(type=archipack_slab_cutter_segment)
+ parts : CollectionProperty(type=archipack_slab_cutter_segment)
def update_points(self, context, o, pts, update_parent=False):
self.auto_update = False
@@ -1291,11 +1291,11 @@ class archipack_slab_cutter(ArchipackCutter, ArchipackObject, Manipulable, Prope
d = archipack_slab.datablock(o.parent)
if d is not None:
- o.parent.select = True
- context.scene.objects.active = o.parent
+ o.parent.select_set(state=True)
+ context.view_layer.objects.active = o.parent
d.update(context)
- o.parent.select = False
- context.scene.objects.active = o
+ o.parent.select_set(state=False)
+ context.view_layer.objects.active = o
class ARCHIPACK_PT_slab(Panel):
@@ -1305,7 +1305,7 @@ class ARCHIPACK_PT_slab(Panel):
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
# bl_context = 'object'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1317,7 +1317,7 @@ class ARCHIPACK_PT_slab(Panel):
if prop is None:
return
layout = self.layout
- layout.operator('archipack.slab_manipulate', icon='HAND')
+ layout.operator('archipack.slab_manipulate', icon='VIEW_PAN')
box = layout.box()
box.operator('archipack.slab_cutter').parent = o.name
box = layout.box()
@@ -1341,7 +1341,7 @@ class ARCHIPACK_PT_slab_cutter(Panel):
bl_label = "Slab Cutter"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1354,7 +1354,7 @@ class ARCHIPACK_PT_slab_cutter(Panel):
layout = self.layout
scene = context.scene
box = layout.box()
- box.operator('archipack.slab_cutter_manipulate', icon='HAND')
+ box.operator('archipack.slab_cutter_manipulate', icon='VIEW_PAN')
box.prop(prop, 'operation', text="")
box = layout.box()
box.label(text="From curve")
@@ -1380,7 +1380,7 @@ class ARCHIPACK_OT_slab_insert(Operator):
bl_description = "Insert part"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- index = IntProperty(default=0)
+ index : IntProperty(default=0)
def execute(self, context):
if context.mode == "OBJECT":
@@ -1400,7 +1400,7 @@ class ARCHIPACK_OT_slab_balcony(Operator):
bl_description = "Insert part"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- index = IntProperty(default=0)
+ index : IntProperty(default=0)
def execute(self, context):
if context.mode == "OBJECT":
@@ -1420,7 +1420,7 @@ class ARCHIPACK_OT_slab_remove(Operator):
bl_description = "Remove part"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- index = IntProperty(default=0)
+ index : IntProperty(default=0)
def execute(self, context):
if context.mode == "OBJECT":
@@ -1452,9 +1452,9 @@ class ARCHIPACK_OT_slab(ArchipackCreateTool, Operator):
d = m.archipack_slab.add()
# make manipulators selectable
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.load_preset(d)
self.add_material(o)
return o
@@ -1467,8 +1467,8 @@ class ARCHIPACK_OT_slab(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = bpy.context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
@@ -1483,7 +1483,7 @@ class ARCHIPACK_OT_slab_from_curve(Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- auto_manipulate = BoolProperty(default=True)
+ auto_manipulate : BoolProperty(default=True)
@classmethod
def poll(self, context):
@@ -1496,12 +1496,12 @@ class ARCHIPACK_OT_slab_from_curve(Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
curve = context.active_object
bpy.ops.archipack.slab(auto_manipulate=self.auto_manipulate)
- o = context.scene.objects.active
+ o = context.view_layer.objects.active
d = archipack_slab.datablock(o)
spline = curve.data.splines[0]
d.from_spline(curve.matrix_world, 12, spline)
@@ -1512,12 +1512,7 @@ class ARCHIPACK_OT_slab_from_curve(Operator):
else:
pt = Vector((0, 0, 0))
# pretranslate
- o.matrix_world = curve.matrix_world * Matrix([
- [1, 0, 0, pt.x],
- [0, 1, 0, pt.y],
- [0, 0, 1, pt.z],
- [0, 0, 0, 1]
- ])
+ o.matrix_world = curve.matrix_world @ Matrix.Translation(pt)
return o
# -----------------------------------------------------
@@ -1540,8 +1535,8 @@ class ARCHIPACK_OT_slab_from_wall(Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- auto_manipulate = BoolProperty(default=True)
- ceiling = BoolProperty(default=False)
+ auto_manipulate : BoolProperty(default=True)
+ ceiling : BoolProperty(default=False)
@classmethod
def poll(self, context):
@@ -1552,7 +1547,7 @@ class ARCHIPACK_OT_slab_from_wall(Operator):
wall = context.active_object
wd = wall.data.archipack_wall2[0]
bpy.ops.archipack.slab(auto_manipulate=False)
- o = context.scene.objects.active
+ o = context.view_layer.objects.active
d = archipack_slab.datablock(o)
d.auto_update = False
d.closed = True
@@ -1576,24 +1571,24 @@ class ARCHIPACK_OT_slab_from_wall(Operator):
[0, 1, 0, 0],
[0, 0, 1, wd.z + d.z],
[0, 0, 0, 1],
- ]) * wall.matrix_world
+ ]) @ wall.matrix_world
else:
o.matrix_world = wall.matrix_world.copy()
bpy.ops.object.select_all(action='DESELECT')
# parenting childs to wall reference point
if wall.parent is None:
x, y, z = wall.bound_box[0]
- context.scene.cursor_location = wall.matrix_world * Vector((x, y, z))
+ context.scene.cursor_location = wall.matrix_world @ Vector((x, y, z))
# fix issue #9
- context.scene.objects.active = wall
+ context.view_layer.objects.active = wall
bpy.ops.archipack.reference_point()
else:
- wall.parent.select = True
- context.scene.objects.active = wall.parent
- wall.select = True
- o.select = True
+ wall.parent.select_set(state=True)
+ context.view_layer.objects.active = wall.parent
+ wall.select_set(state=True)
+ o.select_set(state=True)
bpy.ops.archipack.parent_to_reference()
- wall.parent.select = False
+ wall.parent.select_set(state=False)
return o
@@ -1604,8 +1599,8 @@ class ARCHIPACK_OT_slab_from_wall(Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
if self.auto_manipulate:
bpy.ops.archipack.slab_manipulate('INVOKE_DEFAULT')
return {'FINISHED'}
@@ -1621,7 +1616,7 @@ class ARCHIPACK_OT_slab_cutter(ArchipackCreateTool, Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- parent = StringProperty("")
+ parent : StringProperty("")
def create(self, context):
m = bpy.data.meshes.new("Slab Cutter")
@@ -1636,7 +1631,7 @@ class ARCHIPACK_OT_slab_cutter(ArchipackCreateTool, Operator):
x1, y1, z = bbox[6]
x = 0.2 * (x1 - x0)
y = 0.2 * (y1 - y0)
- o.matrix_world = parent.matrix_world * Matrix([
+ o.matrix_world = parent.matrix_world @ Matrix([
[1, 0, 0, -3 * x],
[0, 1, 0, 0],
[0, 0, 1, 0],
@@ -1659,9 +1654,9 @@ class ARCHIPACK_OT_slab_cutter(ArchipackCreateTool, Operator):
o.location = context.scene.cursor_location
# make manipulators selectable
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
# self.add_material(o)
self.load_preset(d)
update_operation(d, context)
@@ -1674,8 +1669,8 @@ class ARCHIPACK_OT_slab_cutter(ArchipackCreateTool, Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
diff --git a/archipack/archipack_snap.py b/archipack/archipack_snap.py
index 92e09595..33a59041 100644
--- a/archipack/archipack_snap.py
+++ b/archipack/archipack_snap.py
@@ -43,7 +43,7 @@
sp.delta
action_callback(context, event, state, sp)
- state in {'SUCCESS', 'CANCEL'}
+ state in {'RUNNING', 'SUCCESS', 'CANCEL'}
sp.takeloc
sp.placeloc
sp.delta
@@ -64,6 +64,9 @@
import bpy
from bpy.types import Operator
from mathutils import Vector, Matrix
+import logging
+
+logger = logging.getLogger("archipack")
def dumb_callback(context, event, state, sp):
@@ -81,8 +84,8 @@ class SnapStore:
callback = None
draw = None
helper = None
- takeloc = Vector((0, 0, 0))
- placeloc = Vector((0, 0, 0))
+ takeloc = Vector()
+ placeloc = Vector()
constraint_axis = (True, True, False)
helper_matrix = Matrix()
transform_orientation = 'GLOBAL'
@@ -93,20 +96,20 @@ class SnapStore:
act = None
sel = []
use_snap = False
- snap_element = None
+ snap_elements = None
snap_target = None
pivot_point = None
trans_orientation = None
def snap_point(takeloc=None,
- draw=dumb_draw,
- callback=dumb_callback,
- takemat=None,
- constraint_axis=(True, True, False),
- transform_orientation='GLOBAL',
- mode='OBJECT',
- release_confirm=True):
+ draw=None,
+ callback=dumb_callback,
+ takemat=None,
+ constraint_axis=(True, True, False),
+ transform_orientation='GLOBAL',
+ mode='OBJECT',
+ release_confirm=True):
"""
Invoke op from outside world
in a convenient importable function
@@ -126,16 +129,19 @@ def snap_point(takeloc=None,
SnapStore.callback = callback
SnapStore.constraint_axis = constraint_axis
SnapStore.release_confirm = release_confirm
+
if takemat is not None:
SnapStore.helper_matrix = takemat
- takeloc = takemat.translation
+ takeloc = takemat.translation.copy()
transform_orientation = 'LOCAL'
elif takeloc is not None:
- SnapStore.helper_matrix = Matrix().Translation(takeloc)
+ SnapStore.helper_matrix = Matrix.Translation(takeloc)
else:
raise ValueError("ArchipackSnap: Either takeloc or takemat must be defined")
+
SnapStore.takeloc = takeloc
- SnapStore.placeloc = takeloc
+ SnapStore.placeloc = takeloc.copy()
+
SnapStore.transform_orientation = transform_orientation
# @NOTE: unused mode var to switch between OBJECT and EDIT mode
@@ -160,53 +166,56 @@ class ArchipackSnapBase():
- takeloc
- placeloc
"""
+
def __init__(self):
self._draw_handler = None
def init(self, context, event):
# Store context data
- if SnapStore.instances_running < 1:
- SnapStore.sel = [o for o in context.selected_objects]
- SnapStore.act = context.active_object
- bpy.ops.object.select_all(action="DESELECT")
- SnapStore.use_snap = context.tool_settings.use_snap
- SnapStore.snap_element = context.tool_settings.snap_element
- SnapStore.snap_target = context.tool_settings.snap_target
- SnapStore.pivot_point = context.space_data.pivot_point
- SnapStore.trans_orientation = context.space_data.transform_orientation
+ # if SnapStore.instances_running < 1:
+ SnapStore.sel = context.selected_objects[:]
+ SnapStore.act = context.object
+ bpy.ops.object.select_all(action="DESELECT")
+ ts = context.tool_settings
+ SnapStore.use_snap = ts.use_snap
+ SnapStore.snap_elements = ts.snap_elements
+ SnapStore.snap_target = ts.snap_target
+ SnapStore.pivot_point = ts.transform_pivot_point
+ SnapStore.trans_orientation = context.scene.transform_orientation
self.create_helper(context)
- SnapStore.instances_running += 1
- # print("ArchipackSnapBase init: %s" % (SnapStore.instances_running))
- self.set_transform_orientation(context)
- args = (self, context)
- self._draw_handler = bpy.types.SpaceView3D.draw_handler_add(SnapStore.draw, args, 'WINDOW', 'POST_PIXEL')
+ # Use a timer to broadcast a TIMER event while transform.translate is running
+ self._timer = context.window_manager.event_timer_add(0.1, window=context.window)
+
+ if SnapStore.draw is not None:
+ args = (self, context)
+ self._draw_handler = bpy.types.SpaceView3D.draw_handler_add(SnapStore.draw, args, 'WINDOW', 'POST_PIXEL')
+
+ def remove_timer(self, context):
+ if self._timer is not None:
+ context.window_manager.event_timer_remove(self._timer)
def exit(self, context):
- bpy.types.SpaceView3D.draw_handler_remove(self._draw_handler, 'WINDOW')
- # trick to allow launch 2nd instance
- # via callback, preserve context as it
- SnapStore.instances_running -= 1
- # print("ArchipackSnapBase exit: %s" % (SnapStore.instances_running))
- if SnapStore.instances_running > 0:
- return
- self.destroy_helper(context)
+ self.remove_timer(context)
+
+ if self._draw_handler is not None:
+ bpy.types.SpaceView3D.draw_handler_remove(self._draw_handler, 'WINDOW')
+
# Restore original context
- context.tool_settings.use_snap = SnapStore.use_snap
- context.tool_settings.snap_element = SnapStore.snap_element
- context.tool_settings.snap_target = SnapStore.snap_target
- context.space_data.pivot_point = SnapStore.pivot_point
- context.space_data.transform_orientation = SnapStore.trans_orientation
+ if hasattr(context, "tool_settings"):
+ ts = context.tool_settings
+ ts.use_snap = SnapStore.use_snap
+ ts.snap_elements = SnapStore.snap_elements
+ ts.snap_target = SnapStore.snap_target
+ ts.transform_pivot_point = SnapStore.pivot_point
+ context.scene.transform_orientation = SnapStore.trans_orientation
for o in SnapStore.sel:
- o.select = True
+ o.select_set(state=True)
if SnapStore.act is not None:
- context.scene.objects.active = SnapStore.act
-
- def set_transform_orientation(self, context):
- """
- Allow local constraint orientation to be set
- """
- context.space_data.transform_orientation = SnapStore.transform_orientation
+ SnapStore.act.select_set(state=True)
+ context.view_layer.objects.active = SnapStore.act
+ self.destroy_helper(context)
+ logger.debug("Snap.exit %s", context.object.name)
def create_helper(self, context):
"""
@@ -217,23 +226,25 @@ class ArchipackSnapBase():
Do target helper be linked to scene in order to work ?
"""
-
- helper_idx = bpy.data.objects.find('Archipack_snap_helper')
- if helper_idx > -1:
- helper = bpy.data.objects[helper_idx]
- if context.scene.objects.find('Archipack_snap_helper') < 0:
- context.scene.objects.link(helper)
+ helper = bpy.data.objects.get('Archipack_snap_helper')
+ if helper is not None:
+ print("helper found")
+ if context.scene.objects.get('Archipack_snap_helper') is None:
+ print("link helper")
+ # context.scene.collection.objects.link(helper)
+ context.scene.collection.objects.link(helper)
else:
- bpy.ops.object.add(type='MESH')
- helper = context.active_object
- helper.name = 'Archipack_snap_helper'
+ print("create helper")
+ m = bpy.data.meshes.new("Archipack_snap_helper")
+ m.vertices.add(count=1)
+ helper = bpy.data.objects.new("Archipack_snap_helper", m)
+ context.scene.collection.objects.link(helper)
helper.use_fake_user = True
helper.data.use_fake_user = True
- # hide snap helper
- # helper.hide = True
+
helper.matrix_world = SnapStore.helper_matrix
- helper.select = True
- context.scene.objects.active = helper
+ helper.select_set(state=True)
+ context.view_layer.objects.active = helper
SnapStore.helper = helper
def destroy_helper(self, context):
@@ -242,7 +253,8 @@ class ArchipackSnapBase():
currently only support OBJECT mode
"""
if SnapStore.helper is not None:
- context.scene.objects.unlink(SnapStore.helper)
+ # @TODO: Fix this
+ # self.unlink_object_from_scene(context, SnapStore.helper)
SnapStore.helper = None
@property
@@ -266,35 +278,61 @@ class ArchipackSnapBase():
class ARCHIPACK_OT_snap(ArchipackSnapBase, Operator):
bl_idname = 'archipack.snap'
bl_label = 'Archipack snap'
- bl_options = {'UNDO'}
+ bl_options = {'INTERNAL'} # , 'UNDO'
def modal(self, context, event):
- # print("Snap.modal event %s %s" % (event.type, event.value))
+
+ if SnapStore.helper is not None:
+ logger.debug("Snap.modal event %s %s location:%s",
+ event.type,
+ event.value,
+ SnapStore.helper.location)
+
context.area.tag_redraw()
- # NOTE: this part only run after transform LEFTMOUSE RELEASE
- # or with ESC and RIGHTMOUSE
- if event.type not in {'ESC', 'RIGHTMOUSE', 'LEFTMOUSE', 'MOUSEMOVE'}:
- # print("Snap.modal skip unknown event %s %s" % (event.type, event.value))
- # self.report({'WARNING'}, "ARCHIPACK_OT_snap unknown event")
- return{'PASS_THROUGH'}
+
+ if event.type in ('TIMER', 'NOTHING'):
+ SnapStore.callback(context, event, 'RUNNING', self)
+ return {'PASS_THROUGH'}
+
+ if event.type not in ('ESC', 'RIGHTMOUSE', 'LEFTMOUSE', 'MOUSEMOVE', 'INBETWEEN_MOUSEMOVE'):
+ return {'PASS_THROUGH'}
+
if event.type in ('ESC', 'RIGHTMOUSE'):
SnapStore.callback(context, event, 'CANCEL', self)
else:
SnapStore.placeloc = SnapStore.helper.location
- SnapStore.callback(context, event, 'SUCCESS', self)
+ # on tt modal exit with right click, the delta is 0 so exit
+ if self.delta.length == 0:
+ SnapStore.callback(context, event, 'CANCEL', self)
+ else:
+ SnapStore.callback(context, event, 'SUCCESS', self)
+
self.exit(context)
# self.report({'INFO'}, "ARCHIPACK_OT_snap exit")
- return{'FINISHED'}
+ return {'FINISHED'}
def invoke(self, context, event):
if context.area.type == 'VIEW_3D':
- # print("Snap.invoke event %s %s" % (event.type, event.value))
+
+ if event.type in ('ESC', 'RIGHTMOUSE'):
+ return {'FINISHED'}
+
self.init(context, event)
+
+ logger.debug("Snap.invoke event %s %s location:%s act:%s",
+ event.type,
+ event.value,
+ SnapStore.helper.location, context.object.name)
+
context.window_manager.modal_handler_add(self)
+
bpy.ops.transform.translate('INVOKE_DEFAULT',
- constraint_axis=SnapStore.constraint_axis,
- constraint_orientation=SnapStore.transform_orientation,
- release_confirm=SnapStore.release_confirm)
+ constraint_axis=SnapStore.constraint_axis,
+ constraint_orientation=SnapStore.transform_orientation,
+ release_confirm=SnapStore.release_confirm)
+
+ logger.debug("Snap.invoke transform.translate done")
+
return {'RUNNING_MODAL'}
else:
self.report({'WARNING'}, "View3D not found, cannot run operator")
diff --git a/archipack/archipack_stair.py b/archipack/archipack_stair.py
index 94a8da7c..8d512a65 100644
--- a/archipack/archipack_stair.py
+++ b/archipack/archipack_stair.py
@@ -234,16 +234,16 @@ class Stair():
def project_uv(self, rM, uvs, verts, indexes, up_axis='Z'):
if up_axis == 'Z':
- uvs.append([(rM * Vector(verts[i])).to_2d() for i in indexes])
+ uvs.append([(rM @ Vector(verts[i])).to_2d() for i in indexes])
elif up_axis == 'Y':
- uvs.append([(x, z) for x, y, z in [(rM * Vector(verts[i])) for i in indexes]])
+ uvs.append([(x, z) for x, y, z in [(rM @ Vector(verts[i])) for i in indexes]])
else:
- uvs.append([(y, z) for x, y, z in [(rM * Vector(verts[i])) for i in indexes]])
+ uvs.append([(y, z) for x, y, z in [(rM @ Vector(verts[i])) for i in indexes]])
def get_proj_matrix(self, part, t, nose_y):
# a matrix to project verts
# into uv space for horizontal parts of this step
- # so uv = (rM * vertex).to_2d()
+ # so uv = (rM @ vertex).to_2d()
tl = t - nose_y / self.get_length("LEFT")
tr = t - nose_y / self.get_length("RIGHT")
t2, part, dz, shape = self.get_part(tl, "LEFT")
@@ -264,7 +264,7 @@ class Stair():
# a matrix to project verts
# into uv space for horizontal parts of this step
- # so uv = (rM * vertex).to_2d()
+ # so uv = (rM @ vertex).to_2d()
rM = self.get_proj_matrix(self, t, nose_y)
if self.z_mode == 'LINEAR':
@@ -1024,7 +1024,7 @@ class StairGenerator():
co.z += z1
if 'Slope' in g:
co.z += co.y * slope
- verts.append(tM * co)
+ verts.append(tM @ co)
matids += self.user_defined_mat
faces += [tuple([i + f for i in p.vertices]) for p in m.polygons]
uvs += self.user_defined_uvs
@@ -1106,7 +1106,7 @@ class StairGenerator():
if s < n_sections:
v1 = subs[s + 1][0].v.normalized()
dir = (v0 + v1).normalized()
- scale = 1 / cos(0.5 * acos(min(1, max(-1, v0 * v1))))
+ scale = 1 / cos(0.5 * acos(min(1, max(-1, v0.dot(v1)))))
for p in profile:
x, y = n.p + scale * p.x * dir
z = zl + p.y + altitude
@@ -1463,7 +1463,7 @@ class StairGenerator():
if s < n_sections:
v1 = cur_sect[s + 1][0].v.normalized()
dir = (v0 + v1).normalized()
- scale = 1 / cos(0.5 * acos(min(1, max(-1, v0 * v1))))
+ scale = 1 / cos(0.5 * acos(min(1, max(-1, v0.dot(v1)))))
for p in profile:
x, y = n.p + scale * p.x * dir
z = zl + p.y + z_offset
@@ -1546,7 +1546,7 @@ materials_enum = (
class archipack_stair_material(PropertyGroup):
- index = EnumProperty(
+ index : EnumProperty(
items=materials_enum,
default='4',
update=update
@@ -1573,7 +1573,7 @@ class archipack_stair_material(PropertyGroup):
class archipack_stair_part(PropertyGroup):
- type = EnumProperty(
+ type : EnumProperty(
items=(
('S_STAIR', 'Straight stair', '', 0),
('C_STAIR', 'Curved stair', '', 1),
@@ -1585,21 +1585,21 @@ class archipack_stair_part(PropertyGroup):
default='S_STAIR',
update=update_manipulators
)
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
default=2.0,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.01,
default=0.7,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -1607,7 +1607,7 @@ class archipack_stair_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- left_shape = EnumProperty(
+ left_shape : EnumProperty(
items=(
('RECTANGLE', 'Straight', '', 0),
('CIRCLE', 'Curved ', '', 1)
@@ -1615,7 +1615,7 @@ class archipack_stair_part(PropertyGroup):
default='RECTANGLE',
update=update
)
- right_shape = EnumProperty(
+ right_shape : EnumProperty(
items=(
('RECTANGLE', 'Straight', '', 0),
('CIRCLE', 'Curved ', '', 1)
@@ -1623,7 +1623,7 @@ class archipack_stair_part(PropertyGroup):
default='RECTANGLE',
update=update
)
- manipulators = CollectionProperty(type=archipack_manipulator)
+ manipulators : CollectionProperty(type=archipack_manipulator)
def find_datablock_in_selection(self, context):
"""
@@ -1670,69 +1670,69 @@ class archipack_stair_part(PropertyGroup):
class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
- parts = CollectionProperty(type=archipack_stair_part)
- n_parts = IntProperty(
+ parts : CollectionProperty(type=archipack_stair_part)
+ n_parts : IntProperty(
name="Parts",
min=1,
max=32,
default=1, update=update_manipulators
)
- step_depth = FloatProperty(
+ step_depth : FloatProperty(
name="Going",
min=0.2,
default=0.25,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- width = FloatProperty(
+ width : FloatProperty(
name="Width",
min=0.01,
default=1.2,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- height = FloatProperty(
+ height : FloatProperty(
name="Height",
min=0.1,
default=2.4, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- nose_y = FloatProperty(
+ nose_y : FloatProperty(
name="Depth",
min=0.0,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- x_offset = FloatProperty(
+ x_offset : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- nose_z = FloatProperty(
+ nose_z : FloatProperty(
name="Height",
min=0.001,
default=0.03, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- bottom_z = FloatProperty(
+ bottom_z : FloatProperty(
name="Thickness",
min=0.001,
default=0.03, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.5,
default=0.7,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -1740,7 +1740,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- total_angle = FloatProperty(
+ total_angle : FloatProperty(
name="Angle",
min=-50 * pi,
max=50 * pi,
@@ -1748,7 +1748,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- steps_type = EnumProperty(
+ steps_type : EnumProperty(
name="Steps",
items=(
('CLOSED', 'Closed', '', 0),
@@ -1758,7 +1758,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='CLOSED',
update=update
)
- nose_type = EnumProperty(
+ nose_type : EnumProperty(
name="Nosing",
items=(
('STRAIGHT', 'Straight', '', 0),
@@ -1767,7 +1767,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='STRAIGHT',
update=update
)
- left_shape = EnumProperty(
+ left_shape : EnumProperty(
items=(
('RECTANGLE', 'Straight', '', 0),
('CIRCLE', 'Curved ', '', 1)
@@ -1775,7 +1775,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='RECTANGLE',
update=update
)
- right_shape = EnumProperty(
+ right_shape : EnumProperty(
items=(
('RECTANGLE', 'Straight', '', 0),
('CIRCLE', 'Curved ', '', 1)
@@ -1783,7 +1783,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='RECTANGLE',
update=update
)
- z_mode = EnumProperty(
+ z_mode : EnumProperty(
name="Interp z",
items=(
('STANDARD', 'Standard', '', 0),
@@ -1793,7 +1793,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='STANDARD',
update=update
)
- presets = EnumProperty(
+ presets : EnumProperty(
items=(
('STAIR_I', 'I stair', '', 0),
('STAIR_L', 'L stair', '', 1),
@@ -1803,131 +1803,131 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
),
default='STAIR_I', update=update_preset
)
- left_post = BoolProperty(
+ left_post : BoolProperty(
name='left',
default=True,
update=update
)
- right_post = BoolProperty(
+ right_post : BoolProperty(
name='right',
default=True,
update=update
)
- post_spacing = FloatProperty(
+ post_spacing : FloatProperty(
name="Spacing",
min=0.1,
default=1.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_x = FloatProperty(
+ post_x : FloatProperty(
name="Width",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_y = FloatProperty(
+ post_y : FloatProperty(
name="Length",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_z = FloatProperty(
+ post_z : FloatProperty(
name="Height",
min=0.001,
default=1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_alt = FloatProperty(
+ post_alt : FloatProperty(
name="Altitude",
min=-100,
default=0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_offset_x = FloatProperty(
+ post_offset_x : FloatProperty(
name="Offset",
min=-100.0, max=100,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- post_corners = BoolProperty(
+ post_corners : BoolProperty(
name="Only on edges",
update=update,
default=False
)
- user_defined_post_enable = BoolProperty(
+ user_defined_post_enable : BoolProperty(
name="User",
update=update,
default=True
)
- user_defined_post = StringProperty(
+ user_defined_post : StringProperty(
name="User defined",
update=update
)
- idmat_post = EnumProperty(
+ idmat_post : EnumProperty(
name="Post",
items=materials_enum,
default='4',
update=update
)
- left_subs = BoolProperty(
+ left_subs : BoolProperty(
name='left',
default=False,
update=update
)
- right_subs = BoolProperty(
+ right_subs : BoolProperty(
name='right',
default=False,
update=update
)
- subs_spacing = FloatProperty(
+ subs_spacing : FloatProperty(
name="Spacing",
min=0.05,
default=0.10, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_x = FloatProperty(
+ subs_x : FloatProperty(
name="Width",
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_y = FloatProperty(
+ subs_y : FloatProperty(
name="Length",
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_z = FloatProperty(
+ subs_z : FloatProperty(
name="Height",
min=0.001,
default=1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_alt = FloatProperty(
+ subs_alt : FloatProperty(
name="Altitude",
min=-100,
default=0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_offset_x = FloatProperty(
+ subs_offset_x : FloatProperty(
name="Offset",
min=-100.0, max=100,
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- subs_bottom = EnumProperty(
+ subs_bottom : EnumProperty(
name="Bottom",
items=(
('STEP', 'Follow step', '', 0),
@@ -1936,88 +1936,88 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='STEP',
update=update
)
- user_defined_subs_enable = BoolProperty(
+ user_defined_subs_enable : BoolProperty(
name="User",
update=update,
default=True
)
- user_defined_subs = StringProperty(
+ user_defined_subs : StringProperty(
name="User defined",
update=update
)
- idmat_subs = EnumProperty(
+ idmat_subs : EnumProperty(
name="Subs",
items=materials_enum,
default='4',
update=update
)
- left_panel = BoolProperty(
+ left_panel : BoolProperty(
name='left',
default=True,
update=update
)
- right_panel = BoolProperty(
+ right_panel : BoolProperty(
name='right',
default=True,
update=update
)
- panel_alt = FloatProperty(
+ panel_alt : FloatProperty(
name="Altitude",
default=0.25, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_x = FloatProperty(
+ panel_x : FloatProperty(
name="Width",
min=0.001,
default=0.01, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_z = FloatProperty(
+ panel_z : FloatProperty(
name="Height",
min=0.001,
default=0.6, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_dist = FloatProperty(
+ panel_dist : FloatProperty(
name="Spacing",
min=0.001,
default=0.05, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- panel_offset_x = FloatProperty(
+ panel_offset_x : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- idmat_panel = EnumProperty(
+ idmat_panel : EnumProperty(
name="Panels",
items=materials_enum,
default='5',
update=update
)
- left_rail = BoolProperty(
+ left_rail : BoolProperty(
name="left",
update=update,
default=False
)
- right_rail = BoolProperty(
+ right_rail : BoolProperty(
name="right",
update=update,
default=False
)
- rail_n = IntProperty(
+ rail_n : IntProperty(
name="#",
default=1,
min=0,
max=31,
update=update
)
- rail_x = FloatVectorProperty(
+ rail_x : FloatVectorProperty(
name="Width",
default=[
0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05,
@@ -2031,7 +2031,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_z = FloatVectorProperty(
+ rail_z : FloatVectorProperty(
name="Height",
default=[
0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05, 0.05,
@@ -2045,7 +2045,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_offset = FloatVectorProperty(
+ rail_offset : FloatVectorProperty(
name="Offset",
default=[
0, 0, 0, 0, 0, 0, 0, 0,
@@ -2058,7 +2058,7 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_alt = FloatVectorProperty(
+ rail_alt : FloatVectorProperty(
name="Altitude",
default=[
1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0,
@@ -2071,47 +2071,47 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
unit='LENGTH',
update=update
)
- rail_mat = CollectionProperty(type=archipack_stair_material)
+ rail_mat : CollectionProperty(type=archipack_stair_material)
- left_handrail = BoolProperty(
+ left_handrail : BoolProperty(
name="left",
update=update,
default=True
)
- right_handrail = BoolProperty(
+ right_handrail : BoolProperty(
name="right",
update=update,
default=True
)
- handrail_offset = FloatProperty(
+ handrail_offset : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_alt = FloatProperty(
+ handrail_alt : FloatProperty(
name="Altitude",
default=1.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_extend = FloatProperty(
+ handrail_extend : FloatProperty(
name="Extend",
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_slice_left = BoolProperty(
+ handrail_slice_left : BoolProperty(
name='Slice',
default=True,
update=update
)
- handrail_slice_right = BoolProperty(
+ handrail_slice_right : BoolProperty(
name='Slice',
default=True,
update=update
)
- handrail_profil = EnumProperty(
+ handrail_profil : EnumProperty(
name="Profil",
items=(
('SQUARE', 'Square', '', 0),
@@ -2121,21 +2121,21 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
default='SQUARE',
update=update
)
- handrail_x = FloatProperty(
+ handrail_x : FloatProperty(
name="Width",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_y = FloatProperty(
+ handrail_y : FloatProperty(
name="Height",
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- handrail_radius = FloatProperty(
+ handrail_radius : FloatProperty(
name="Radius",
min=0.001,
default=0.02, precision=2, step=1,
@@ -2143,85 +2143,85 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
update=update
)
- left_string = BoolProperty(
+ left_string : BoolProperty(
name="left",
update=update,
default=False
)
- right_string = BoolProperty(
+ right_string : BoolProperty(
name="right",
update=update,
default=False
)
- string_x = FloatProperty(
+ string_x : FloatProperty(
name="Width",
min=-100.0,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- string_z = FloatProperty(
+ string_z : FloatProperty(
name="Height",
default=0.3, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- string_offset = FloatProperty(
+ string_offset : FloatProperty(
name="Offset",
default=0.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- string_alt = FloatProperty(
+ string_alt : FloatProperty(
name="Altitude",
default=-0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- idmat_bottom = EnumProperty(
+ idmat_bottom : EnumProperty(
name="Bottom",
items=materials_enum,
default='1',
update=update
)
- idmat_raise = EnumProperty(
+ idmat_raise : EnumProperty(
name="Raise",
items=materials_enum,
default='1',
update=update
)
- idmat_step_front = EnumProperty(
+ idmat_step_front : EnumProperty(
name="Step front",
items=materials_enum,
default='3',
update=update
)
- idmat_top = EnumProperty(
+ idmat_top : EnumProperty(
name="Top",
items=materials_enum,
default='3',
update=update
)
- idmat_side = EnumProperty(
+ idmat_side : EnumProperty(
name="Side",
items=materials_enum,
default='1',
update=update
)
- idmat_step_side = EnumProperty(
+ idmat_step_side : EnumProperty(
name="Step Side",
items=materials_enum,
default='3',
update=update
)
- idmat_handrail = EnumProperty(
+ idmat_handrail : EnumProperty(
name="Handrail",
items=materials_enum,
default='3',
update=update
)
- idmat_string = EnumProperty(
+ idmat_string : EnumProperty(
name="String",
items=materials_enum,
default='3',
@@ -2229,35 +2229,35 @@ class archipack_stair(ArchipackObject, Manipulable, PropertyGroup):
)
# UI layout related
- parts_expand = BoolProperty(
+ parts_expand : BoolProperty(
default=False
)
- steps_expand = BoolProperty(
+ steps_expand : BoolProperty(
default=False
)
- rail_expand = BoolProperty(
+ rail_expand : BoolProperty(
default=False
)
- idmats_expand = BoolProperty(
+ idmats_expand : BoolProperty(
default=False
)
- handrail_expand = BoolProperty(
+ handrail_expand : BoolProperty(
default=False
)
- string_expand = BoolProperty(
+ string_expand : BoolProperty(
default=False
)
- post_expand = BoolProperty(
+ post_expand : BoolProperty(
default=False
)
- panel_expand = BoolProperty(
+ panel_expand : BoolProperty(
default=False
)
- subs_expand = BoolProperty(
+ subs_expand : BoolProperty(
default=False
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
@@ -2539,7 +2539,7 @@ class ARCHIPACK_PT_stair(Panel):
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
# bl_context = 'object'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -2552,7 +2552,7 @@ class ARCHIPACK_PT_stair(Panel):
scene = context.scene
layout = self.layout
row = layout.row(align=True)
- row.operator('archipack.stair_manipulate', icon='HAND')
+ row.operator('archipack.stair_manipulate', icon='VIEW_PAN')
row = layout.row(align=True)
row.prop(prop, 'presets', text="")
box = layout.box()
@@ -2560,8 +2560,8 @@ class ARCHIPACK_PT_stair(Panel):
row = box.row(align=True)
# row.menu("ARCHIPACK_MT_stair_preset", text=bpy.types.ARCHIPACK_MT_stair_preset.bl_label)
row.operator("archipack.stair_preset_menu", text=bpy.types.ARCHIPACK_OT_stair_preset_menu.bl_label)
- row.operator("archipack.stair_preset", text="", icon='ZOOMIN')
- row.operator("archipack.stair_preset", text="", icon='ZOOMOUT').remove_active = True
+ row.operator("archipack.stair_preset", text="", icon='ADD')
+ row.operator("archipack.stair_preset", text="", icon='REMOVE').remove_active = True
box = layout.box()
box.prop(prop, 'width')
box.prop(prop, 'height')
@@ -2753,9 +2753,9 @@ class ARCHIPACK_OT_stair(ArchipackCreateTool, Operator):
m = bpy.data.meshes.new("Stair")
o = bpy.data.objects.new("Stair", m)
d = m.archipack_stair.add()
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.load_preset(d)
self.add_material(o)
m.auto_smooth_angle = 0.20944
@@ -2769,8 +2769,8 @@ class ARCHIPACK_OT_stair(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
diff --git a/archipack/archipack_thumbs.py b/archipack/archipack_thumbs.py
index bfc9d55e..cd5ced6d 100644
--- a/archipack/archipack_thumbs.py
+++ b/archipack/archipack_thumbs.py
@@ -33,38 +33,30 @@ def log(s):
print("[log]" + s)
-def generateThumb(context, cls, preset):
- log("### RENDER THUMB ############################")
- log("Start generating: " + cls)
+def create_lamp(context, loc):
+ bpy.ops.object.light_add(
+ type='POINT',
+ radius=1,
+ view_align=False,
+ location=loc)
+ lamp = context.active_object
+ lamp.data.use_nodes = True
+ tree = lamp.data.node_tree
+ return tree, tree.nodes
- # engine settings
- context.scene.render.engine = 'CYCLES'
- render = context.scene.cycles
- render.progressive = 'PATH'
- render.samples = 24
- try:
- render.use_square_samples = True
- except:
- pass
- render.preview_samples = 24
- render.aa_samples = 24
- render.transparent_max_bounces = 8
- render.transparent_min_bounces = 8
- render.transmission_bounces = 8
- render.max_bounces = 8
- render.min_bounces = 6
- render.caustics_refractive = False
- render.caustics_reflective = False
- render.use_transparent_shadows = True
- render.diffuse_bounces = 1
- render.glossy_bounces = 4
- bpy.ops.object.select_all(action="SELECT")
- bpy.ops.object.delete()
- # create object, loading preset
- getattr(bpy.ops.archipack, cls)('INVOKE_DEFAULT', filepath=preset, auto_manipulate=False)
- o = context.active_object
- size = o.dimensions
+def create_camera(context, loc, rot):
+ bpy.ops.object.camera_add(
+ view_align=True,
+ enter_editmode=False,
+ location=loc,
+ rotation=rot)
+ cam = context.active_object
+ context.scene.camera = cam
+ return cam
+
+
+def get_center(o):
x, y, z = o.bound_box[0]
min_x = x
min_y = y
@@ -73,27 +65,90 @@ def generateThumb(context, cls, preset):
max_x = x
max_y = y
max_z = z
- center = Vector((
+ return Vector((
min_x + 0.5 * (max_x - min_x),
min_y + 0.5 * (max_y - min_y),
min_z + 0.5 * (max_z - min_z)))
- # oposite / tan (0.5 * fov) where fov is 49.134 deg
+
+def apply_simple_material(o, name, color):
+ m = bpy.data.materials.new(name)
+ m.use_nodes = True
+ m.node_tree.nodes[1].inputs[0].default_value = color
+ o.data.materials.append(m)
+
+
+# /home/stephen/blender-28-git/build_linux_full/bin/blender --background --factory-startup -noaudio --python /home/stephen/blender-28-git/build_linux_full/bin/2.80/scripts/addons/archipack/archipack_thumbs.py -- addon:archipack matlib:/medias/stephen/DATA/lib/ cls:roof preset:/home/stephen/.config/blender/2.80/scripts/presets/archipack_roof/square.py
+
+
+def generateThumb(context, cls, preset, engine):
+ log("### RENDER THUMB ############################")
+
+ # Cleanup scene
+ for o in context.scene.objects:
+ o.select_set(state=True)
+
+ bpy.ops.object.delete()
+
+ log("Start generating: %s" % cls)
+
+ # setup render
+
+ context.scene.render.engine = engine
+
+ if engine == 'CYCLES':
+ cycles = context.scene.cycles
+ cycles.progressive = 'PATH'
+ cycles.samples = 24
+ try:
+ cycles.use_square_samples = True
+ except:
+ pass
+ cycles.preview_samples = 24
+ cycles.aa_samples = 24
+ cycles.transparent_max_bounces = 8
+ cycles.transparent_min_bounces = 8
+ cycles.transmission_bounces = 8
+ cycles.max_bounces = 8
+ cycles.min_bounces = 6
+ cycles.caustics_refractive = False
+ cycles.caustics_reflective = False
+ cycles.use_transparent_shadows = True
+ cycles.diffuse_bounces = 1
+ cycles.glossy_bounces = 4
+
+ elif engine == 'BLENDER_EEVEE':
+ eevee = context.scene.eevee
+
+ else:
+ raise RuntimeError("Unsupported render engine %s" % engine)
+
+ render = context.scene.render
+
+ # engine settings
+ render.resolution_x = 150
+ render.resolution_y = 100
+ render.filepath = preset[:-3] + ".png"
+
+ # create object, loading preset
+ getattr(bpy.ops.archipack, cls)('INVOKE_DEFAULT', filepath=preset, auto_manipulate=False)
+ o = context.active_object
+ size = o.dimensions
+ center = get_center(o)
+
+ # opposite / tan (0.5 * fov) where fov is 49.134 deg
dist = max(size) / 0.32
- loc = center + dist * Vector((0.5, -1, 0.5)).normalized()
+ loc = center + dist * Vector((-0.5, -1, 0.5)).normalized()
log("Prepare camera")
- bpy.ops.object.camera_add(view_align=True,
- enter_editmode=False,
- location=loc,
- rotation=(1.150952, 0.0, 0.462509))
- cam = context.active_object
+ cam = create_camera(context, loc, (1.150952, 0.0, -0.462509))
cam.data.lens = 50
- cam.select = True
- context.scene.camera = cam
- bpy.ops.object.select_all(action="DESELECT")
- o.select = True
+ for ob in context.scene.objects:
+ ob.select_set(state=False)
+
+ o.select_set(state=True)
+
bpy.ops.view3d.camera_to_view_selected()
log("Prepare scene")
@@ -103,63 +158,33 @@ def generateThumb(context, cls, preset):
view_align=False,
enter_editmode=False,
location=(0, 0, 0)
- )
+ )
+
p = context.active_object
- m = bpy.data.materials.new("Plane")
- m.use_nodes = True
- m.node_tree.nodes[1].inputs[0].default_value = (1, 1, 1, 1)
- p.data.materials.append(m)
+ apply_simple_material(p, "Plane", (1, 1, 1, 1))
# add 3 lights
- bpy.ops.object.light_add(
- type='POINT',
- radius=1,
- view_align=False,
- location=(3.69736, -7, 6.0))
- l = context.active_object
- l.data.use_nodes = True
- tree = l.data.node_tree
- nodes = l.data.node_tree.nodes
+ tree, nodes = create_lamp(context, (3.69736, -7, 6.0))
emit = nodes["Emission"]
emit.inputs[1].default_value = 2000.0
- bpy.ops.object.light_add(
- type='POINT',
- radius=1,
- view_align=False,
- location=(9.414563179016113, 5.446230888366699, 5.903861999511719))
- l = context.active_object
- l.data.use_nodes = True
- tree = l.data.node_tree
- nodes = l.data.node_tree.nodes
+ tree, nodes = create_lamp(context, (9.414563179016113, 5.446230888366699, 5.903861999511719))
emit = nodes["Emission"]
falloff = nodes.new(type="ShaderNodeLightFalloff")
falloff.inputs[0].default_value = 5
tree.links.new(falloff.outputs[2], emit.inputs[1])
- bpy.ops.object.light_add(
- type='POINT',
- radius=1,
- view_align=False,
- location=(-7.847615718841553, 1.03135085105896, 5.903861999511719))
- l = context.active_object
- l.data.use_nodes = True
- tree = l.data.node_tree
- nodes = l.data.node_tree.nodes
+ tree, nodes = create_lamp(context, (-7.847615718841553, 1.03135085105896, 5.903861999511719))
emit = nodes["Emission"]
falloff = nodes.new(type="ShaderNodeLightFalloff")
falloff.inputs[0].default_value = 5
tree.links.new(falloff.outputs[2], emit.inputs[1])
# Set output filename.
- render = context.scene.render
- render.filepath = preset[:-3] + ".png"
render.use_file_extension = True
render.use_overwrite = True
render.use_compositing = False
render.use_sequencer = False
- render.resolution_x = 150
- render.resolution_y = 100
render.resolution_percentage = 100
# render.image_settings.file_format = 'PNG'
# render.image_settings.color_mode = 'RGBA'
@@ -175,8 +200,9 @@ def generateThumb(context, cls, preset):
if __name__ == "__main__":
- preset = ""
+ preset = ""
+ engine = 'BLENDER_EEVEE' #'CYCLES'
for arg in sys.argv:
if arg.startswith("cls:"):
cls = arg[4:]
@@ -186,9 +212,14 @@ if __name__ == "__main__":
matlib = arg[7:]
if arg.startswith("addon:"):
module = arg[6:]
+ if arg.startswith("engine:"):
+ engine = arg[7:]
try:
+ # log("### ENABLE %s ADDON ############################" % module)
bpy.ops.wm.addon_enable(module=module)
+ # log("### MATLIB PATH ############################")
bpy.context.user_preferences.addons[module].preferences.matlib_path = matlib
except:
raise RuntimeError("module name not found")
- generateThumb(bpy.context, cls, preset)
+ # log("### GENERATE ############################")
+ generateThumb(bpy.context, cls, preset, engine)
diff --git a/archipack/archipack_truss.py b/archipack/archipack_truss.py
index b8056daa..c8fe8768 100644
--- a/archipack/archipack_truss.py
+++ b/archipack/archipack_truss.py
@@ -43,7 +43,7 @@ def update(self, context):
class archipack_truss(ArchipackObject, Manipulable, PropertyGroup):
- truss_type = EnumProperty(
+ truss_type : EnumProperty(
name="Type",
items=(
('1', 'Prolyte E20', 'Prolyte E20', 0),
@@ -57,40 +57,40 @@ class archipack_truss(ArchipackObject, Manipulable, PropertyGroup):
default='2',
update=update
)
- z = FloatProperty(
+ z : FloatProperty(
name="Height",
default=2.0, min=0.01,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- segs = IntProperty(
+ segs : IntProperty(
name="Segs",
default=6, min=3,
update=update
)
- master_segs = IntProperty(
+ master_segs : IntProperty(
name="Master Segs",
default=1, min=1,
update=update
)
- master_count = IntProperty(
+ master_count : IntProperty(
name="Masters",
default=3, min=2,
update=update
)
- entre_axe = FloatProperty(
+ entre_axe : FloatProperty(
name="Distance",
default=0.239, min=0.001,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- master_radius = FloatProperty(
+ master_radius : FloatProperty(
name="Radius",
default=0.02415, min=0.0001,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- slaves_radius = FloatProperty(
+ slaves_radius : FloatProperty(
name="Subs radius",
default=0.01, min=0.0001,
unit='LENGTH', subtype='DISTANCE',
@@ -101,7 +101,7 @@ class archipack_truss(ArchipackObject, Manipulable, PropertyGroup):
# .auto_update = False
# bulk changes
# .auto_update = True
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update
@@ -127,10 +127,10 @@ class archipack_truss(ArchipackObject, Manipulable, PropertyGroup):
if not add:
for seg in range(segs):
- verts.append(tM * tMb * tmpverts[seg])
+ verts.append(tM @ tMb @ tmpverts[seg])
for seg in range(segs):
- verts.append(tM * tMt * tmpverts[seg])
+ verts.append(tM @ tMt @ tmpverts[seg])
for seg in range(segs - 1):
f = cv + seg
@@ -280,7 +280,7 @@ class ARCHIPACK_PT_truss(Panel):
bl_label = "Truss"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -292,7 +292,7 @@ class ARCHIPACK_PT_truss(Panel):
return
layout = self.layout
row = layout.row(align=True)
- row.operator('archipack.truss_manipulate', icon='HAND')
+ row.operator('archipack.truss_manipulate', icon='VIEW_PAN')
box = layout.box()
box.prop(prop, 'truss_type')
box.prop(prop, 'z')
@@ -318,9 +318,9 @@ class ARCHIPACK_OT_truss(ArchipackCreateTool, Operator):
d = m.archipack_truss.add()
# make manipulators selectable
# d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.load_preset(d)
self.add_material(o)
m.auto_smooth_angle = 1.15
@@ -334,8 +334,8 @@ class ARCHIPACK_OT_truss(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = bpy.context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
diff --git a/archipack/archipack_wall2.py b/archipack/archipack_wall2.py
index 1506e171..09836780 100644
--- a/archipack/archipack_wall2.py
+++ b/archipack/archipack_wall2.py
@@ -45,11 +45,14 @@ from .archipack_manipulator import (
GlPolygon, GlPolyline,
GlLine, GlText, FeedbackPanel
)
-from .archipack_object import ArchipackObject, ArchipackCreateTool, ArchpackDrawTool
+from .archipack_object import ArchipackObject, ArchipackCreateTool, ArchipackDrawTool
from .archipack_2d import Line, Arc
from .archipack_snap import snap_point
from .archipack_keymaps import Keymaps
+import logging
+logger = logging.getLogger("archipack")
+
class Wall():
def __init__(self, wall_z, z, t, flip):
@@ -323,7 +326,7 @@ class WallGenerator():
for i in range(idx_from + 1, len(self.segs)):
seg = self.segs[i]
seg.rotate(a)
- dp = rM * (seg.p0 - p0)
+ dp = rM @ (seg.p0 - p0)
seg.translate(dp)
def translate(self, idx_from, dp):
@@ -338,7 +341,7 @@ class WallGenerator():
"""
move shape fromTM into toTM coordsys
"""
- dp = (toTM.inverted() * fromTM.translation).to_2d()
+ dp = (toTM.inverted() @ fromTM.translation).to_2d()
da = toTM.row[1].to_2d().angle_signed(fromTM.row[1].to_2d())
ca = cos(da)
sa = sin(da)
@@ -347,7 +350,7 @@ class WallGenerator():
[sa, ca]
])
for s in self.segs:
- tp = (rM * s.p0) - s.p0 + dp
+ tp = (rM @ s.p0) - s.p0 + dp
s.rotate(da)
s.translate(tp)
@@ -446,27 +449,27 @@ def update_t_part(self, context):
if o.parent is None:
# create a reference point and make it active
x, y, z = w.bound_box[0]
- context.scene.cursor_location = w.matrix_world * Vector((x, y, z))
+ context.scene.cursor_location = w.matrix_world @ Vector((x, y, z))
# fix issue #9
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
bpy.ops.archipack.reference_point()
- o.select = True
+ o.select_set(state=True)
else:
- context.scene.objects.active = o.parent
- w.select = True
+ context.view_layer.objects.active = o.parent
+ w.select_set(state=True)
else:
# w has parent
if o.parent is not w.parent:
link_to_parent = True
- context.scene.objects.active = w.parent
- o.select = True
+ context.view_layer.objects.active = w.parent
+ o.select_set(state=True)
if o.parent is not None:
# store o.parent to delete it
to_delete = o.parent
for c in o.parent.children:
if c is not o:
c.hide_select = False
- c.select = True
+ c.select_set(state=True)
parent = context.active_object
@@ -487,11 +490,11 @@ def update_t_part(self, context):
])
# dir in absolute world coordsys
- dir = orM * og.segs[0].straight(1, 0).v
+ dir = orM @ og.segs[0].straight(1, 0).v
# pt in w coordsys
pos = otM.translation
- pt = (wtM.inverted() * pos).to_2d()
+ pt = (wtM.inverted() @ pos).to_2d()
for wall_idx, wall in enumerate(wg.segs):
res, dist, t = wall.point_sur_segment(pt)
@@ -504,8 +507,8 @@ def update_t_part(self, context):
# rotation here is wrong when w has not parent while o has parent
if res and t > 0 and t < 1 and abs(dist) < dmax:
- x = wrM * wall.straight(1, t).v
- y = wrM * wall.normal(t).v.normalized()
+ x = wrM @ wall.straight(1, t).v
+ y = wrM @ wall.normal(t).v.normalized()
self.parts[0].a0 = dir.angle_signed(x)
o.matrix_world = Matrix([
[x.x, -y.x, 0, pos.x],
@@ -531,8 +534,8 @@ def update_t_part(self, context):
# delete unneeded reference point
if to_delete is not None:
bpy.ops.object.select_all(action="DESELECT")
- to_delete.select = True
- context.scene.objects.active = to_delete
+ to_delete.select_set(state=True)
+ context.view_layer.objects.active = to_delete
if bpy.ops.object.delete.poll():
bpy.ops.object.delete(use_global=False)
@@ -624,7 +627,7 @@ def update_type(self, context):
class archipack_wall2_part(PropertyGroup):
- type = EnumProperty(
+ type : EnumProperty(
items=(
('S_WALL', 'Straight', '', 0),
('C_WALL', 'Curved', '', 1)
@@ -632,21 +635,21 @@ class archipack_wall2_part(PropertyGroup):
default='S_WALL',
update=update_type
)
- length = FloatProperty(
+ length : FloatProperty(
name="Length",
min=0.01,
default=2.0,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.5,
default=0.7,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- a0 = FloatProperty(
+ a0 : FloatProperty(
name="Start angle",
min=-pi,
max=pi,
@@ -654,7 +657,7 @@ class archipack_wall2_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -662,7 +665,7 @@ class archipack_wall2_part(PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- z = FloatVectorProperty(
+ z : FloatVectorProperty(
name="Height",
default=[
0, 0, 0, 0, 0, 0, 0, 0,
@@ -673,7 +676,7 @@ class archipack_wall2_part(PropertyGroup):
size=31,
update=update
)
- t = FloatVectorProperty(
+ t : FloatVectorProperty(
name="Position",
min=0,
max=1,
@@ -686,24 +689,24 @@ class archipack_wall2_part(PropertyGroup):
size=31,
update=update
)
- splits = IntProperty(
+ splits : IntProperty(
name="Splits",
default=1,
min=1,
max=31,
get=get_splits, set=set_splits
)
- n_splits = IntProperty(
+ n_splits : IntProperty(
name="Splits",
default=1,
min=1,
max=31,
update=update
)
- auto_update = BoolProperty(default=True)
- manipulators = CollectionProperty(type=archipack_manipulator)
+ auto_update : BoolProperty(default=True)
+ manipulators : CollectionProperty(type=archipack_manipulator)
# ui related
- expand = BoolProperty(default=False)
+ expand : BoolProperty(default=False)
def _set_t(self, splits):
t = 1 / splits
@@ -766,11 +769,11 @@ class archipack_wall2_part(PropertyGroup):
class archipack_wall2_child(PropertyGroup):
# Size Loc
# Delta Loc
- manipulators = CollectionProperty(type=archipack_manipulator)
- child_name = StringProperty()
- wall_idx = IntProperty()
- pos = FloatVectorProperty(subtype='XYZ')
- flip = BoolProperty(default=False)
+ manipulators : CollectionProperty(type=archipack_manipulator)
+ child_name : StringProperty()
+ wall_idx : IntProperty()
+ pos : FloatVectorProperty(subtype='XYZ')
+ flip : BoolProperty(default=False)
def get_child(self, context):
d = None
@@ -785,14 +788,14 @@ class archipack_wall2_child(PropertyGroup):
class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
- parts = CollectionProperty(type=archipack_wall2_part)
- n_parts = IntProperty(
+ parts : CollectionProperty(type=archipack_wall2_part)
+ n_parts : IntProperty(
name="Parts",
min=1,
max=1024,
default=1, update=update_manipulators
)
- step_angle = FloatProperty(
+ step_angle : FloatProperty(
description="Curved parts segmentation",
name="Step angle",
min=1 / 180 * pi,
@@ -801,34 +804,34 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- width = FloatProperty(
+ width : FloatProperty(
name="Width",
min=0.01,
default=0.2,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- z = FloatProperty(
+ z : FloatProperty(
name='Height',
min=0.1,
default=2.7, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='height', update=update,
)
- x_offset = FloatProperty(
+ x_offset : FloatProperty(
name="Offset",
min=-1, max=1,
default=-1, precision=2, step=1,
update=update
)
- radius = FloatProperty(
+ radius : FloatProperty(
name="Radius",
min=0.5,
default=0.7,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- da = FloatProperty(
+ da : FloatProperty(
name="Angle",
min=-pi,
max=pi,
@@ -836,32 +839,32 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
subtype='ANGLE', unit='ROTATION',
update=update
)
- flip = BoolProperty(
+ flip : BoolProperty(
name="Flip",
default=False,
update=update_childs
)
- closed = BoolProperty(
+ closed : BoolProperty(
default=False,
name="Close",
update=update_manipulators
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update_manipulators
)
- realtime = BoolProperty(
+ realtime : BoolProperty(
options={'SKIP_SAVE'},
default=True,
name="Real Time",
description="Relocate childs in realtime"
)
# dumb manipulators to show sizes between childs
- childs_manipulators = CollectionProperty(type=archipack_manipulator)
+ childs_manipulators : CollectionProperty(type=archipack_manipulator)
# store to manipulate windows and doors
- childs = CollectionProperty(type=archipack_wall2_child)
- t_part = StringProperty(
+ childs : CollectionProperty(type=archipack_wall2_child)
+ t_part : StringProperty(
name="Parent wall",
description="This part will follow parent when set",
default="",
@@ -1014,18 +1017,18 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
def interpolate_bezier(self, pts, wM, p0, p1, resolution):
if resolution == 0:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
v = (p1.co - p0.co).normalized()
d1 = (p0.handle_right - p0.co).normalized()
d2 = (p1.co - p1.handle_left).normalized()
if d1 == v and d2 == v:
- pts.append(wM * p0.co.to_3d())
+ pts.append(wM @ p0.co.to_3d())
else:
- seg = interpolate_bezier(wM * p0.co,
- wM * p0.handle_right,
- wM * p1.handle_left,
- wM * p1.co,
+ seg = interpolate_bezier(wM @ p0.co,
+ wM @ p0.handle_right,
+ wM @ p1.handle_left,
+ wM @ p1.co,
resolution + 1)
for i in range(resolution):
pts.append(seg[i].to_3d())
@@ -1041,7 +1044,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
def from_spline(self, wM, resolution, spline):
pts = []
if spline.type == 'POLY':
- pts = [wM * p.co.to_3d() for p in spline.points]
+ pts = [wM @ p.co.to_3d() for p in spline.points]
if spline.use_cyclic_u:
pts.append(pts[0])
elif spline.type == 'BEZIER':
@@ -1056,7 +1059,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
self.interpolate_bezier(pts, wM, p0, p1, resolution)
pts.append(pts[0])
else:
- pts.append(wM * points[-1].co)
+ pts.append(wM @ points[-1].co)
if self.is_cw(pts):
pts = list(reversed(pts))
@@ -1134,7 +1137,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
if not self.closed:
dp = pts[0] - pts[-1]
# pre-translate as dp is in local coordsys
- o.matrix_world = o.matrix_world * Matrix([
+ o.matrix_world = o.matrix_world @ Matrix([
[1, 0, 0, dp.x],
[0, 1, 0, dp.y],
[0, 0, 1, 0],
@@ -1326,7 +1329,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
# pt in w coordsys
pos = ctM.translation
- pt = (witM * pos).to_2d()
+ pt = (witM @ pos).to_2d()
for wall_idx, wall in enumerate(g.segs):
# may be optimized with a bound check
@@ -1337,7 +1340,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
# p0
if res and t > 0 and t < 1 and abs(dist) < dmax:
# dir in world coordsys
- dir = wrM * wall.sized_normal(t, 1).v
+ dir = wrM @ wall.sized_normal(t, 1).v
wall_with_childs[wall_idx] = 1
m = self.childs_manipulators.add()
m.type_key = 'DUMB_SIZE'
@@ -1345,14 +1348,14 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
if "archipack_window" in cd:
flip = self.flip
else:
- dir_y = crM * Vector((0, -1))
+ dir_y = crM @ Vector((0, -1))
# let door orient where user want
flip = (dir_y - dir).length > 0.5
# store z in wall space
relocate.append((
child.name,
wall_idx,
- (t * wall.length, dist, (witM * pos).z),
+ (t * wall.length, dist, (witM @ pos).z),
flip,
t))
break
@@ -1392,19 +1395,19 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
if d is not None:
# print("change flip:%s width:%s" % (d.flip != child.flip, d.y != self.width))
if d.y != self.width or d.flip != child.flip:
- c.select = True
+ c.select_set(state=True)
d.auto_update = False
d.flip = child.flip
d.y = self.width
d.auto_update = True
- c.select = False
+ c.select_set(state=False)
x, y = n.p - (0.5 * w * n.v)
else:
x, y = n.p - (child.pos.y * n.v)
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
# preTranslate
- c.matrix_world = tM * Matrix([
+ c.matrix_world = tM @ Matrix([
[rx, -ry, 0, x],
[ry, rx, 0, y],
[0, 0, 1, child.pos.z],
@@ -1445,7 +1448,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
# child is either a window or a door
wall_has_childs = True
dt = 0.5 * d.x / wall.length
- pt = (itM * c.matrix_world.translation).to_2d()
+ pt = (itM @ c.matrix_world.translation).to_2d()
res, y, t = wall.point_sur_segment(pt)
child.pos = (wall.length * t, y, child.pos.z)
p1 = wall.lerp(t - dt)
@@ -1503,7 +1506,7 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
if o.parent is not None:
for c in o.parent.children:
if (archipack_wall2.datablock(c) == self):
- context.scene.objects.active = c
+ context.view_layer.objects.active = c
found = True
break
if found:
@@ -1522,12 +1525,12 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
if o.parent is None:
return
g = self.get_generator()
- itM = o.matrix_world.inverted() * o.parent.matrix_world
+ itM = o.matrix_world.inverted() @ o.parent.matrix_world
for child in self.childs:
c, d = child.get_child(context)
if d is not None:
wall = g.segs[child.wall_idx]
- pt = (itM * c.location).to_2d()
+ pt = (itM @ c.location).to_2d()
res, d, t = wall.point_sur_segment(pt)
child.pos = (t * wall.length, d, child.pos.z)
# update childs manipulators
@@ -1631,14 +1634,14 @@ class archipack_wall2(ArchipackObject, Manipulable, PropertyGroup):
tM = o.matrix_world
up = Vector((0, 0, 1))
for seg in g.segs:
- p = tM * seg.p0.to_3d()
+ p = tM @ seg.p0.to_3d()
p.z = 0.01
# prevent self intersect
- o.hide = True
+ o.hide_viewport = True
res, pos, normal, face_index, r, matrix_world = context.scene.ray_cast(
p,
up)
- o.hide = False
+ o.hide_viewport = False
# print("res:%s" % res)
if res and r.data is not None and "archipack_roof" in r.data:
return r, r.data.archipack_roof[0]
@@ -1659,7 +1662,7 @@ class ARCHIPACK_OT_wall2_throttle_update(Operator):
bl_idname = "archipack.wall2_throttle_update"
bl_label = "Update childs with a delay"
- name = StringProperty()
+ name : StringProperty()
def modal(self, context, event):
global update_timer_updating
@@ -1671,7 +1674,7 @@ class ARCHIPACK_OT_wall2_throttle_update(Operator):
if o is not None:
m = o.modifiers.get("AutoBoolean")
if m is not None:
- o.hide = False
+ o.hide_viewport = False
# o.display_type = 'TEXTURED'
# m.show_viewport = True
@@ -1709,7 +1712,7 @@ class ARCHIPACK_PT_wall2(Panel):
bl_label = "Wall"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
def draw(self, context):
prop = archipack_wall2.datablock(context.object)
@@ -1717,7 +1720,7 @@ class ARCHIPACK_PT_wall2(Panel):
return
layout = self.layout
row = layout.row(align=True)
- row.operator("archipack.wall2_manipulate", icon='HAND')
+ row.operator("archipack.wall2_manipulate", icon='VIEW_PAN')
# row = layout.row(align=True)
# row.prop(prop, 'realtime')
box = layout.box()
@@ -1765,11 +1768,11 @@ class ARCHIPACK_OT_wall2(ArchipackCreateTool, Operator):
o = bpy.data.objects.new("Wall", m)
d = m.archipack_wall2.add()
d.manipulable_selectable = True
- context.scene.objects.link(o)
- o.select = True
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
# around 12 degree
m.auto_smooth_angle = 0.20944
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
self.load_preset(d)
self.add_material(o)
return o
@@ -1779,8 +1782,8 @@ class ARCHIPACK_OT_wall2(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = bpy.context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
return {'FINISHED'}
else:
@@ -1795,7 +1798,7 @@ class ARCHIPACK_OT_wall2_from_curve(Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- auto_manipulate = BoolProperty(default=True)
+ auto_manipulate : BoolProperty(default=True)
@classmethod
def poll(self, context):
@@ -1805,7 +1808,7 @@ class ARCHIPACK_OT_wall2_from_curve(Operator):
curve = context.active_object
for spline in curve.data.splines:
bpy.ops.archipack.wall2(auto_manipulate=self.auto_manipulate)
- o = context.scene.objects.active
+ o = context.view_layer.objects.active
d = archipack_wall2.datablock(o)
d.from_spline(curve.matrix_world, 12, spline)
if spline.type == 'POLY':
@@ -1815,7 +1818,7 @@ class ARCHIPACK_OT_wall2_from_curve(Operator):
else:
pt = Vector((0, 0, 0))
# pretranslate
- o.matrix_world = curve.matrix_world * Matrix([
+ o.matrix_world = curve.matrix_world @ Matrix([
[1, 0, 0, pt.x],
[0, 1, 0, pt.y],
[0, 0, 1, pt.z],
@@ -1831,8 +1834,8 @@ class ARCHIPACK_OT_wall2_from_curve(Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
if o is not None:
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -1846,7 +1849,7 @@ class ARCHIPACK_OT_wall2_from_slab(Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- auto_manipulate = BoolProperty(default=True)
+ auto_manipulate : BoolProperty(default=True)
@classmethod
def poll(self, context):
@@ -1857,7 +1860,7 @@ class ARCHIPACK_OT_wall2_from_slab(Operator):
slab = context.active_object
wd = slab.data.archipack_slab[0]
bpy.ops.archipack.wall2(auto_manipulate=self.auto_manipulate)
- o = context.scene.objects.active
+ o = context.view_layer.objects.active
d = archipack_wall2.datablock(o)
d.auto_update = False
d.parts.clear()
@@ -1873,8 +1876,8 @@ class ARCHIPACK_OT_wall2_from_slab(Operator):
p.radius = part.radius
p.da = part.da
p.a0 = part.a0
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
d.auto_update = True
# pretranslate
o.matrix_world = slab.matrix_world.copy()
@@ -1883,17 +1886,17 @@ class ARCHIPACK_OT_wall2_from_slab(Operator):
# parenting childs to wall reference point
if o.parent is None:
x, y, z = o.bound_box[0]
- context.scene.cursor_location = o.matrix_world * Vector((x, y, z))
+ context.scene.cursor_location = o.matrix_world @ Vector((x, y, z))
# fix issue #9
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
bpy.ops.archipack.reference_point()
else:
- o.parent.select = True
- context.scene.objects.active = o.parent
- o.select = True
- slab.select = True
+ o.parent.select_set(state=True)
+ context.view_layer.objects.active = o.parent
+ o.select_set(state=True)
+ slab.select_set(state=True)
bpy.ops.archipack.parent_to_reference()
- o.parent.select = False
+ o.parent.select_set(state=False)
return o
# -----------------------------------------------------
@@ -1903,8 +1906,8 @@ class ARCHIPACK_OT_wall2_from_slab(Operator):
if context.mode == "OBJECT":
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
@@ -1918,7 +1921,7 @@ class ARCHIPACK_OT_wall2_fit_roof(Operator):
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- inside = BoolProperty(default=False)
+ inside : BoolProperty(default=False)
@classmethod
def poll(self, context):
@@ -1939,12 +1942,11 @@ class ARCHIPACK_OT_wall2_fit_roof(Operator):
# ------------------------------------------------------------------
-class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
+class ARCHIPACK_OT_wall2_draw(ArchipackDrawTool, Operator):
bl_idname = "archipack.wall2_draw"
bl_label = "Draw a Wall"
- bl_description = "Draw a Wall"
+ bl_description = "Create a wall by drawing its baseline in 3D view"
bl_category = 'Archipack'
- bl_options = {'REGISTER', 'UNDO'}
o = None
state = 'RUNNING'
@@ -1993,7 +1995,7 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
self.line.draw(context)
def sp_callback(self, context, event, state, sp):
- # print("sp_callback event %s %s state:%s" % (event.type, event.value, state))
+ logger.debug("ARCHIPACK_OT_wall2_draw.sp_callback event %s %s state:%s", event.type, event.value, state)
if state == 'SUCCESS':
@@ -2004,19 +2006,21 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
takeloc = sp.takeloc
delta = sp.delta
- old = context.active_object
+ old = context.object
if self.o is None:
bpy.ops.archipack.wall2(auto_manipulate=False)
- o = context.active_object
+ o = context.object
o.location = takeloc
self.o = o
d = archipack_wall2.datablock(o)
+
part = d.parts[0]
part.length = delta.length
else:
o = self.o
- o.select = True
- context.scene.objects.active = o
+ # select and make active
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
d = archipack_wall2.datablock(o)
# Check for end close to start and close when applicable
dp = sp.placeloc - o.location
@@ -2031,7 +2035,7 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
rM = o.matrix_world.inverted().to_3x3()
g = d.get_generator()
w = g.segs[-2]
- dp = rM * delta
+ dp = rM @ delta
da = atan2(dp.y, dp.x) - w.straight(1).angle
a0 = part.a0 + da
if a0 > pi:
@@ -2039,8 +2043,10 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
if a0 < -pi:
a0 += 2 * pi
part.a0 = a0
+ d.update(context)
- context.scene.objects.active = old
+ old.select_set(state=True)
+ context.view_layer.objects.active = old
self.flag_next = True
context.area.tag_redraw()
# print("feedback.on:%s" % self.feedback.on)
@@ -2051,7 +2057,7 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
# print("sp_init event %s %s %s" % (event.type, event.value, state))
if state == 'SUCCESS':
# point placed, check if a wall was under mouse
- res, tM, wall, y = self.mouse_hover_wall(context, event)
+ res, tM, wall, width, y, z_offset = self.mouse_hover_wall(context, event)
if res:
d = archipack_wall2.datablock(wall)
if event.ctrl:
@@ -2078,8 +2084,8 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
so reverse order here when needed
"""
d = archipack_wall2.datablock(self.o)
- g = d.get_generator()
- pts = [seg.p0.to_3d() for seg in g.segs]
+ g = d.get_generator(axis=False)
+ pts = [seg.p0 for seg in g.segs]
if d.closed:
pts.append(pts[0])
@@ -2094,46 +2100,70 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
def modal(self, context, event):
context.area.tag_redraw()
- # print("modal event %s %s" % (event.type, event.value))
- if event.type == 'NONE':
+ if event.type in {'NONE', 'TIMER', 'EVT_TWEAK_L', 'WINDOW_DEACTIVATE'}:
return {'PASS_THROUGH'}
- if self.state == 'STARTING':
- takeloc = self.mouse_to_plane(context, event)
- # wait for takeloc being visible when button is over horizon
- rv3d = context.region_data
- viewinv = rv3d.view_matrix.inverted()
+ if self.keymap.check(event, self.keymap.delete):
+ self.feedback.disable()
+ bpy.types.SpaceView3D.draw_handler_remove(self._handle, 'WINDOW')
+ self.o = None
+ return {'FINISHED', 'PASS_THROUGH'}
- if (takeloc * viewinv).z < 0 or not rv3d.is_perspective:
- # print("STARTING")
+ if self.state == 'STARTING' and event.type not in {'ESC', 'RIGHTMOUSE'}:
+ # wait for takeloc being visible when button is over horizon
+ takeloc = self.mouse_to_plane(context, event)
+ if takeloc is not None:
+ logger.debug("ARCHIPACK_OT_wall2_draw.modal(STARTING) location:%s", takeloc)
snap_point(takeloc=takeloc,
- callback=self.sp_init,
- constraint_axis=(True, True, False),
- release_confirm=True)
+ callback=self.sp_init,
+ constraint_axis=(True, True, False),
+ release_confirm=True)
return {'RUNNING_MODAL'}
elif self.state == 'RUNNING':
# print("RUNNING")
+ logger.debug("ARCHIPACK_OT_wall2_draw.modal(RUNNING) location:%s", self.takeloc)
self.state = 'CREATE'
snap_point(takeloc=self.takeloc,
- draw=self.sp_draw,
- takemat=self.takemat,
- transform_orientation=context.space_data.transform_orientation,
- callback=self.sp_callback,
- constraint_axis=(True, True, False),
- release_confirm=self.max_style_draw_tool)
+ draw=self.sp_draw,
+ takemat=self.takemat,
+ transform_orientation=context.scene.transform_orientation,
+ callback=self.sp_callback,
+ constraint_axis=(True, True, False),
+ release_confirm=self.max_style_draw_tool)
return {'RUNNING_MODAL'}
+ elif self.state != 'CANCEL' and event.type in {'C', 'c'}:
+
+ logger.debug("ARCHIPACK_OT_wall2_draw.modal(%s) C pressed", self.state)
+ self.feedback.disable()
+ bpy.types.SpaceView3D.draw_handler_remove(self._handle, 'WINDOW')
+
+ o = self.o
+ # select and make active
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
+
+ d = archipack_wall2.datablock(o)
+ d.closed = True
+
+ if bpy.ops.archipack.manipulate.poll():
+ bpy.ops.archipack.manipulate('INVOKE_DEFAULT')
+
+ return {'FINISHED'}
+
elif self.state != 'CANCEL' and event.type in {'LEFTMOUSE', 'RET', 'NUMPAD_ENTER', 'SPACE'}:
# print('LEFTMOUSE %s' % (event.value))
self.feedback.instructions(context, "Draw a wall", "Click & Drag to add a segment", [
+ ('ENTER', 'Add part'),
+ ('BACK_SPACE', 'Remove part'),
('CTRL', 'Snap'),
+ ('C', 'Close wall and exit'),
('MMBTN', 'Constraint to axis'),
('X Y', 'Constraint to axis'),
- ('BACK_SPACE', 'Remove part'),
('RIGHTCLICK or ESC', 'exit')
- ])
+ ])
# press with max mode release with blender mode
if self.max_style_draw_tool:
@@ -2146,74 +2176,85 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
if self.flag_next:
self.flag_next = False
o = self.o
- o.select = True
- context.scene.objects.active = o
+
+ # select and make active
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
+
d = archipack_wall2.datablock(o)
g = d.get_generator()
p0 = g.segs[-2].p0
p1 = g.segs[-2].p1
dp = p1 - p0
- takemat = o.matrix_world * Matrix([
+ takemat = o.matrix_world @ Matrix([
[dp.x, dp.y, 0, p1.x],
[dp.y, -dp.x, 0, p1.y],
[0, 0, 1, 0],
[0, 0, 0, 1]
])
- takeloc = o.matrix_world * p1.to_3d()
- o.select = False
+ takeloc = o.matrix_world @ p1.to_3d()
+ o.select_set(state=False)
else:
- takeloc = self.mouse_to_plane(context, event)
takemat = None
+ takeloc = self.mouse_to_plane(context, event)
- snap_point(takeloc=takeloc,
- takemat=takemat,
- draw=self.sp_draw,
- callback=self.sp_callback,
- constraint_axis=(True, True, False),
- release_confirm=self.max_style_draw_tool)
+ if takeloc is not None:
+ logger.debug("ARCHIPACK_OT_wall2_draw.modal(CREATE) location:%s", takeloc)
+
+ snap_point(takeloc=takeloc,
+ takemat=takemat,
+ draw=self.sp_draw,
+ callback=self.sp_callback,
+ constraint_axis=(True, True, False),
+ release_confirm=self.max_style_draw_tool)
return {'RUNNING_MODAL'}
if self.keymap.check(event, self.keymap.undo) or (
event.type in {'BACK_SPACE'} and event.value == 'RELEASE'
- ):
+ ):
if self.o is not None:
o = self.o
- o.select = True
- context.scene.objects.active = o
+
+ # select and make active
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
d = archipack_wall2.datablock(o)
if d.n_parts > 1:
d.n_parts -= 1
return {'RUNNING_MODAL'}
if self.state == 'CANCEL' or (event.type in {'ESC', 'RIGHTMOUSE'} and
- event.value == 'RELEASE'):
+ event.value == 'RELEASE'):
self.feedback.disable()
bpy.types.SpaceView3D.draw_handler_remove(self._handle, 'WINDOW')
-
+ logger.debug("ARCHIPACK_OT_wall2_draw.modal(CANCEL) %s", event.type)
if self.o is None:
- context.scene.objects.active = self.act
for o in self.sel:
- o.select = True
+ o.select_set(state=True)
+ # select and make active
+ self.act.select_set(state=True)
+ context.view_layer.objects.active = self.act
+
else:
- self.o.select = True
- context.scene.objects.active = self.o
+ o = self.o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
# remove last segment with blender mode
- d = archipack_wall2.datablock(self.o)
+ d = archipack_wall2.datablock(o)
if not self.max_style_draw_tool:
if not d.closed and d.n_parts > 1:
d.n_parts -= 1
-
- self.o.select = True
- context.scene.objects.active = self.o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
# make T child
if self.parent is not None:
d.t_part = self.parent
- if bpy.ops.archipack.wall2_manipulate.poll():
- bpy.ops.archipack.wall2_manipulate('INVOKE_DEFAULT')
+ if bpy.ops.archipack.manipulate.poll():
+ bpy.ops.archipack.manipulate('INVOKE_DEFAULT')
return {'FINISHED'}
@@ -2236,11 +2277,11 @@ class ARCHIPACK_OT_wall2_draw(ArchpackDrawTool, Operator):
('X Y', 'Constraint to axis'),
('SHIFT+CTRL+TAB', 'Switch snap mode'),
('RIGHTCLICK or ESC', 'exit without change')
- ])
+ ])
self.feedback.enable()
args = (self, context)
- self.sel = [o for o in context.selected_objects]
+ self.sel = context.selected_objects[:]
self.act = context.active_object
bpy.ops.object.select_all(action="DESELECT")
@@ -2265,7 +2306,7 @@ class ARCHIPACK_OT_wall2_insert(Operator):
bl_description = "Insert part"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- index = IntProperty(default=0)
+ index : IntProperty(default=0)
def execute(self, context):
if context.mode == "OBJECT":
@@ -2286,7 +2327,7 @@ class ARCHIPACK_OT_wall2_remove(Operator):
bl_description = "Remove part"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- index = IntProperty(default=0)
+ index : IntProperty(default=0)
def execute(self, context):
if context.mode == "OBJECT":
@@ -2352,8 +2393,8 @@ class ARCHIPACK_OT_wall2_manipulate(Operator):
d.setup_childs(o, g)
d.update_childs(context, o, g)
d.update(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
diff --git a/archipack/archipack_window.py b/archipack/archipack_window.py
index 1bf349db..618344b4 100644
--- a/archipack/archipack_window.py
+++ b/archipack/archipack_window.py
@@ -41,7 +41,7 @@ from .archipack_handle import create_handle, window_handle_vertical_01, window_h
from .archipack_manipulator import Manipulable
from .archipack_preset import ArchipackPreset, PresetMenuOperator
from .archipack_gl import FeedbackPanel
-from .archipack_object import ArchipackObject, ArchipackCreateTool, ArchpackDrawTool
+from .archipack_object import ArchipackObject, ArchipackCreateTool, ArchipackDrawTool
from .archipack_keymaps import Keymaps
@@ -71,7 +71,7 @@ def get_cols(self):
class archipack_window_panelrow(PropertyGroup):
- width = FloatVectorProperty(
+ width : FloatVectorProperty(
name="Width",
min=0.5,
max=100.0,
@@ -84,7 +84,7 @@ class archipack_window_panelrow(PropertyGroup):
size=31,
update=update
)
- fixed = BoolVectorProperty(
+ fixed : BoolVectorProperty(
name="Fixed",
default=[
False, False, False, False, False, False, False, False,
@@ -95,7 +95,7 @@ class archipack_window_panelrow(PropertyGroup):
size=32,
update=update
)
- cols = IntProperty(
+ cols : IntProperty(
name="Panels",
description="number of panels getter and setter, to avoid infinite recursion",
min=1,
@@ -103,7 +103,7 @@ class archipack_window_panelrow(PropertyGroup):
default=2,
get=get_cols, set=set_cols
)
- n_cols = IntProperty(
+ n_cols : IntProperty(
name="Panels",
description="store number of panels, internal use only to avoid infinite recursion",
min=1,
@@ -111,14 +111,14 @@ class archipack_window_panelrow(PropertyGroup):
default=2,
update=update
)
- height = FloatProperty(
+ height : FloatProperty(
name="Height",
min=0.1,
default=1.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
update=update
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
name="auto_update",
description="disable auto update to avoid infinite recursion",
@@ -188,19 +188,19 @@ class archipack_window_panelrow(PropertyGroup):
class archipack_window_panel(ArchipackObject, PropertyGroup):
- center = FloatVectorProperty(
+ center : FloatVectorProperty(
subtype='XYZ'
)
- origin = FloatVectorProperty(
+ origin : FloatVectorProperty(
subtype='XYZ'
)
- size = FloatVectorProperty(
+ size : FloatVectorProperty(
subtype='XYZ'
)
- radius = FloatVectorProperty(
+ radius : FloatVectorProperty(
subtype='XYZ'
)
- angle_y = FloatProperty(
+ angle_y : FloatProperty(
name='angle',
unit='ROTATION',
subtype='ANGLE',
@@ -208,27 +208,27 @@ class archipack_window_panel(ArchipackObject, PropertyGroup):
default=0, precision=2,
description='angle'
)
- frame_y = FloatProperty(
+ frame_y : FloatProperty(
name='Depth',
min=0,
default=0.06, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='frame depth'
)
- frame_x = FloatProperty(
+ frame_x : FloatProperty(
name='Width',
min=0,
default=0.06, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='frame width'
)
- curve_steps = IntProperty(
+ curve_steps : IntProperty(
name="curve steps",
min=1,
max=128,
default=1
)
- shape = EnumProperty(
+ shape : EnumProperty(
name='Shape',
items=(
('RECTANGLE', 'Rectangle', '', 0),
@@ -239,19 +239,19 @@ class archipack_window_panel(ArchipackObject, PropertyGroup):
),
default='RECTANGLE'
)
- pivot = FloatProperty(
+ pivot : FloatProperty(
name='pivot',
min=-1, max=1,
default=-1, precision=2,
description='pivot'
)
- side_material = IntProperty(
+ side_material : IntProperty(
name="side material",
min=0,
max=2,
default=0
)
- handle = EnumProperty(
+ handle : EnumProperty(
name='Shape',
items=(
('NONE', 'No handle', '', 0),
@@ -260,24 +260,24 @@ class archipack_window_panel(ArchipackObject, PropertyGroup):
),
default='NONE'
)
- handle_model = IntProperty(
+ handle_model : IntProperty(
name="handle model",
default=1,
min=1,
max=2
)
- handle_altitude = FloatProperty(
+ handle_altitude : FloatProperty(
name='handle altitude',
min=0,
default=0.2, precision=2,
unit='LENGTH', subtype='DISTANCE',
description='handle altitude'
)
- fixed = BoolProperty(
+ fixed : BoolProperty(
name="Fixed",
default=False
)
- enable_glass = BoolProperty(
+ enable_glass : BoolProperty(
name="Enable glass",
default=True
)
@@ -404,7 +404,7 @@ class archipack_window_panel(ArchipackObject, PropertyGroup):
def remove_handle(self, context, o):
handle = self.find_handle(o)
if handle is not None:
- context.scene.objects.unlink(handle)
+ context.scene.collection.objects.unlink(handle)
bpy.data.objects.remove(handle, do_unlink=True)
def update(self, context):
@@ -425,28 +425,28 @@ class archipack_window_panel(ArchipackObject, PropertyGroup):
class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
- x = FloatProperty(
+ x : FloatProperty(
name='Width',
min=0.25,
default=100.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='Width', update=update
)
- y = FloatProperty(
+ y : FloatProperty(
name='Depth',
min=0.1,
default=0.20, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='Depth', update=update,
)
- z = FloatProperty(
+ z : FloatProperty(
name='Height',
min=0.1,
default=1.2, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='height', update=update,
)
- angle_y = FloatProperty(
+ angle_y : FloatProperty(
name='Angle',
unit='ROTATION',
subtype='ANGLE',
@@ -454,179 +454,179 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
default=0, precision=2,
description='angle', update=update,
)
- radius = FloatProperty(
+ radius : FloatProperty(
name='Radius',
min=0.1,
default=2.5, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='radius', update=update,
)
- elipsis_b = FloatProperty(
+ elipsis_b : FloatProperty(
name='Ellipsis',
min=0.1,
default=0.5, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='ellipsis vertical size', update=update,
)
- altitude = FloatProperty(
+ altitude : FloatProperty(
name='Altitude',
default=1.0, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='altitude', update=update,
)
- offset = FloatProperty(
+ offset : FloatProperty(
name='Offset',
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='offset', update=update,
)
- frame_y = FloatProperty(
+ frame_y : FloatProperty(
name='Depth',
min=0,
default=0.06, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame depth', update=update,
)
- frame_x = FloatProperty(
+ frame_x : FloatProperty(
name='Width',
min=0,
default=0.06, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame width', update=update,
)
- out_frame = BoolProperty(
+ out_frame : BoolProperty(
name="Out frame",
default=False, update=update,
)
- out_frame_y = FloatProperty(
+ out_frame_y : FloatProperty(
name='Side depth',
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame side depth', update=update,
)
- out_frame_y2 = FloatProperty(
+ out_frame_y2 : FloatProperty(
name='Front depth',
min=0.001,
default=0.02, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame front depth', update=update,
)
- out_frame_x = FloatProperty(
+ out_frame_x : FloatProperty(
name='Front Width',
min=0.0,
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='frame width set to 0 disable front frame', update=update,
)
- out_frame_offset = FloatProperty(
+ out_frame_offset : FloatProperty(
name='Offset',
min=0.0,
default=0.0, precision=3, step=0.1,
unit='LENGTH', subtype='DISTANCE',
description='frame offset', update=update,
)
- out_tablet_enable = BoolProperty(
+ out_tablet_enable : BoolProperty(
name="Out tablet",
default=True, update=update,
)
- out_tablet_x = FloatProperty(
+ out_tablet_x : FloatProperty(
name='Width',
min=0.0,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='tablet width', update=update,
)
- out_tablet_y = FloatProperty(
+ out_tablet_y : FloatProperty(
name='Depth',
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='tablet depth', update=update,
)
- out_tablet_z = FloatProperty(
+ out_tablet_z : FloatProperty(
name='Height',
min=0.001,
default=0.03, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='tablet height', update=update,
)
- in_tablet_enable = BoolProperty(
+ in_tablet_enable : BoolProperty(
name="In tablet",
default=True, update=update,
)
- in_tablet_x = FloatProperty(
+ in_tablet_x : FloatProperty(
name='Width',
min=0.0,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='tablet width', update=update,
)
- in_tablet_y = FloatProperty(
+ in_tablet_y : FloatProperty(
name='Depth',
min=0.001,
default=0.04, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='tablet depth', update=update,
)
- in_tablet_z = FloatProperty(
+ in_tablet_z : FloatProperty(
name='Height',
min=0.001,
default=0.03, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='tablet height', update=update,
)
- blind_enable = BoolProperty(
+ blind_enable : BoolProperty(
name="Blind",
default=False, update=update,
)
- blind_y = FloatProperty(
+ blind_y : FloatProperty(
name='Depth',
min=0.001,
default=0.002, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='Store depth', update=update,
)
- blind_z = FloatProperty(
+ blind_z : FloatProperty(
name='Height',
min=0.001,
default=0.03, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='Store height', update=update,
)
- blind_open = FloatProperty(
+ blind_open : FloatProperty(
name='Open',
min=0.0, max=100,
default=80, precision=1,
subtype='PERCENTAGE',
description='Store open', update=update,
)
- rows = CollectionProperty(type=archipack_window_panelrow)
- n_rows = IntProperty(
+ rows : CollectionProperty(type=archipack_window_panelrow)
+ n_rows : IntProperty(
name="Number of rows",
min=1,
max=32,
default=1, update=update,
)
- curve_steps = IntProperty(
+ curve_steps : IntProperty(
name="Steps",
min=6,
max=128,
default=16, update=update,
)
- hole_outside_mat = IntProperty(
+ hole_outside_mat : IntProperty(
name="Outside",
min=0,
max=128,
default=0, update=update,
)
- hole_inside_mat = IntProperty(
+ hole_inside_mat : IntProperty(
name="Inside",
min=0,
max=128,
default=1, update=update,
)
- window_shape = EnumProperty(
+ window_shape : EnumProperty(
name='Shape',
items=(
('RECTANGLE', 'Rectangle', '', 0),
@@ -637,7 +637,7 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
),
default='RECTANGLE', update=update,
)
- window_type = EnumProperty(
+ window_type : EnumProperty(
name='Type',
items=(
('FLAT', 'Flat window', '', 0),
@@ -645,59 +645,59 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
),
default='FLAT', update=update,
)
- enable_glass = BoolProperty(
+ enable_glass : BoolProperty(
name="Enable glass",
default=True,
update=update
)
- warning = BoolProperty(
+ warning : BoolProperty(
options={'SKIP_SAVE'},
name="Warning",
default=False
)
- handle_enable = BoolProperty(
+ handle_enable : BoolProperty(
name='Handle',
default=True, update=update_childs,
)
- handle_altitude = FloatProperty(
+ handle_altitude : FloatProperty(
name="Altitude",
min=0,
default=1.4, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='handle altitude', update=update_childs,
)
- hole_margin = FloatProperty(
+ hole_margin : FloatProperty(
name='Hole margin',
min=0.0,
default=0.1, precision=2, step=1,
unit='LENGTH', subtype='DISTANCE',
description='how much hole surround wall'
)
- flip = BoolProperty(
+ flip : BoolProperty(
default=False,
update=update,
description='flip outside and outside material of hole'
)
# layout related
- display_detail = BoolProperty(
+ display_detail : BoolProperty(
options={'SKIP_SAVE'},
default=False
)
- display_panels = BoolProperty(
+ display_panels : BoolProperty(
options={'SKIP_SAVE'},
default=True
)
- display_materials = BoolProperty(
+ display_materials : BoolProperty(
options={'SKIP_SAVE'},
default=True
)
- auto_update = BoolProperty(
+ auto_update : BoolProperty(
options={'SKIP_SAVE'},
default=True,
update=update
)
- portal = BoolProperty(
+ portal : BoolProperty(
default=False,
name="Portal",
description="Generate a portal",
@@ -1002,7 +1002,7 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
lamp = self.find_portal(o)
if self.portal:
if lamp is None:
- bpy.ops.object.light_add(type='AREA')
+ bpy.ops.object.lamp_add(type='AREA')
lamp = context.active_object
lamp.name = "Portal"
lamp.parent = o
@@ -1019,15 +1019,15 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
[0, 1, 0, 0.5 * self.z + self.altitude],
[0, 0, 0, 1]
])
- lamp.matrix_world = o.matrix_world * tM
+ lamp.matrix_world = o.matrix_world @ tM
elif lamp is not None:
d = lamp.data
- context.scene.objects.unlink(lamp)
+ context.scene.collection.objects.unlink(lamp)
bpy.data.objects.remove(lamp)
bpy.data.lights.remove(d)
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
def setup_manipulators(self):
if len(self.manipulators) == 4:
@@ -1054,13 +1054,13 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
if archipack_window_panel.filter(child):
to_remove -= 1
self.remove_handle(context, child)
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child, do_unlink=True)
def remove_handle(self, context, o):
handle = self.find_handle(o)
if handle is not None:
- context.scene.objects.unlink(handle)
+ context.scene.collection.objects.unlink(handle)
bpy.data.objects.remove(handle, do_unlink=True)
def update_rows(self, context, o):
@@ -1127,7 +1127,7 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
id = c_names.index(c.data.name)
except:
self.remove_handle(context, c)
- context.scene.objects.unlink(c)
+ context.scene.collection.objects.unlink(c)
bpy.data.objects.remove(c, do_unlink=True)
# children ordering may not be the same, so get the right l_childs order
@@ -1145,7 +1145,7 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
for i, child in enumerate(childs):
if order[i] < 0:
p = bpy.data.objects.new("Panel", child.data)
- context.scene.objects.link(p)
+ context.scene.collection.objects.link(p)
p.lock_location[0] = True
p.lock_location[1] = True
p.lock_location[2] = True
@@ -1169,20 +1169,20 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
h = create_handle(context, p, handle.data)
h.location = handle.location.copy()
elif h is not None:
- context.scene.objects.unlink(h)
+ context.scene.collection.objects.unlink(h)
bpy.data.objects.remove(h, do_unlink=True)
p.location = child.location.copy()
# restore context
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
def _synch_hole(self, context, linked, hole):
l_hole = self.find_hole(linked)
if l_hole is None:
l_hole = bpy.data.objects.new("hole", hole.data)
l_hole['archipack_hole'] = True
- context.scene.objects.link(l_hole)
+ context.scene.collection.objects.link(l_hole)
for mat in hole.data.materials:
l_hole.data.materials.append(mat)
l_hole.parent = linked
@@ -1196,8 +1196,8 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
synch childs nodes of linked objects
"""
bpy.ops.object.select_all(action='DESELECT')
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
childs = self.get_childs_panels(context, o)
hole = self.find_hole(o)
bpy.ops.object.select_linked(type='OBDATA')
@@ -1296,8 +1296,8 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
else:
child = childs[child_n - 1]
- child.select = True
- context.scene.objects.active = child
+ child.select_set(state=True)
+ context.view_layer.objects.active = child
props = archipack_window_panel.datablock(child)
if props is not None:
props.origin = Vector((origin[panel].x, offset.y, 0))
@@ -1442,7 +1442,7 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
if hole_obj is None:
m = bpy.data.meshes.new("hole")
hole_obj = bpy.data.objects.new("hole", m)
- context.scene.objects.link(hole_obj)
+ context.scene.collection.objects.link(hole_obj)
hole_obj['archipack_hole'] = True
hole_obj.parent = o
hole_obj.matrix_world = o.matrix_world.copy()
@@ -1496,11 +1496,11 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
m = bpy.data.meshes.new("hole")
o = bpy.data.objects.new("hole", m)
o['archipack_robusthole'] = True
- context.scene.objects.link(o)
+ context.scene.collection.objects.link(o)
verts = hole.vertices(self.curve_steps, Vector((0, self.altitude, 0)), center, origin, size, radius,
self.angle_y, 0, shape_z=shape_z, path_type=self.shape)
- verts = [tM * Vector(v) for v in verts]
+ verts = [tM @ Vector(v) for v in verts]
faces = hole.faces(self.curve_steps, path_type=self.shape)
@@ -1511,8 +1511,8 @@ class archipack_window(ArchipackObject, Manipulable, PropertyGroup):
bmed.buildmesh(context, o, verts, faces, matids=matids, uvs=uvs)
# MaterialUtils.add_wall2_materials(o)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return o
@@ -1522,13 +1522,13 @@ class ARCHIPACK_PT_window(Panel):
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
# bl_context = 'object'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
# layout related
- display_detail = BoolProperty(
+ display_detail : BoolProperty(
default=False
)
- display_panels = BoolProperty(
+ display_panels : BoolProperty(
default=True
)
@@ -1542,7 +1542,7 @@ class ARCHIPACK_PT_window(Panel):
if prop is None:
return
layout = self.layout
- layout.operator('archipack.window_manipulate', icon='HAND')
+ layout.operator('archipack.window_manipulate', icon='VIEW_PAN')
row = layout.row(align=True)
row.operator('archipack.window', text="Refresh", icon='FILE_REFRESH').mode = 'REFRESH'
if o.data.users > 1:
@@ -1552,8 +1552,8 @@ class ARCHIPACK_PT_window(Panel):
# box.label(text="Styles")
row = box.row(align=True)
row.operator("archipack.window_preset_menu", text=bpy.types.ARCHIPACK_OT_window_preset_menu.bl_label)
- row.operator("archipack.window_preset", text="", icon='ZOOMIN')
- row.operator("archipack.window_preset", text="", icon='ZOOMOUT').remove_active = True
+ row.operator("archipack.window_preset", text="", icon='ADD')
+ row.operator("archipack.window_preset", text="", icon='REMOVE').remove_active = True
box = layout.box()
box.prop(prop, 'window_type')
box.prop(prop, 'x')
@@ -1587,7 +1587,7 @@ class ARCHIPACK_PT_window(Panel):
box = layout.box()
box.prop(prop, 'enable_glass')
box = layout.box()
- box.label("Frame")
+ box.label(text="Frame")
box.prop(prop, 'frame_x')
box.prop(prop, 'frame_y')
if prop.window_shape != 'CIRCLE':
@@ -1654,7 +1654,7 @@ class ARCHIPACK_PT_window(Panel):
row.prop(prop, "display_materials", icon="TRIA_RIGHT", icon_only=True, text="Materials", emboss=False)
if prop.display_materials:
box = layout.box()
- box.label("Hole")
+ box.label(text="Hole")
box.prop(prop, 'hole_inside_mat')
box.prop(prop, 'hole_outside_mat')
@@ -1666,7 +1666,7 @@ class ARCHIPACK_PT_window_panel(Panel):
bl_label = "Window panel"
bl_space_type = 'VIEW_3D'
bl_region_type = 'UI'
- bl_category = 'ArchiPack'
+ bl_category = 'Archipack'
@classmethod
def poll(cls, context):
@@ -1688,31 +1688,31 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
bl_description = "Window"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- x = FloatProperty(
+ x : FloatProperty(
name='width',
min=0.1, max=10000,
default=2.0, precision=2,
description='Width'
)
- y = FloatProperty(
+ y : FloatProperty(
name='depth',
min=0.1, max=10000,
default=0.20, precision=2,
description='Depth'
)
- z = FloatProperty(
+ z : FloatProperty(
name='height',
min=0.1, max=10000,
default=1.2, precision=2,
description='height'
)
- altitude = FloatProperty(
+ altitude : FloatProperty(
name='altitude',
min=0.0, max=10000,
default=1.0, precision=2,
description='altitude'
)
- mode = EnumProperty(
+ mode : EnumProperty(
items=(
('CREATE', 'Create', '', 0),
('DELETE', 'Delete', '', 1),
@@ -1721,12 +1721,12 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
),
default='CREATE'
)
- # auto_manipulate = BoolProperty(default=True)
+ # auto_manipulate : BoolProperty(default=True)
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
m = bpy.data.meshes.new("Window")
@@ -1736,14 +1736,14 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
d.y = self.y
d.z = self.z
d.altitude = self.altitude
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.add_material(o)
self.load_preset(d)
# select frame
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return o
def delete(self, context):
@@ -1753,20 +1753,20 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
for child in o.children:
if child.type == 'LIGHT':
d = child.data
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child)
bpy.data.lights.remove(d)
elif 'archipack_hole' in child:
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child, do_unlink=True)
elif child.data is not None and 'archipack_window_panel' in child.data:
for handle in child.children:
if 'archipack_handle' in handle:
- context.scene.objects.unlink(handle)
+ context.scene.collection.objects.unlink(handle)
bpy.data.objects.remove(handle, do_unlink=True)
- context.scene.objects.unlink(child)
+ context.scene.collection.objects.unlink(child)
bpy.data.objects.remove(child, do_unlink=True)
- context.scene.objects.unlink(o)
+ context.scene.collection.objects.unlink(o)
bpy.data.objects.remove(o, do_unlink=True)
def update(self, context):
@@ -1780,8 +1780,8 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
archipack_window.datablock(linked).update(context)
bpy.ops.object.select_all(action="DESELECT")
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
def unique(self, context):
act = context.active_object
@@ -1789,13 +1789,13 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
for o in sel:
if archipack_window.filter(o):
- o.select = True
+ o.select_set(state=True)
for child in o.children:
if 'archipack_hole' in child or (
child.data is not None and
'archipack_window_panel' in child.data):
child.hide_select = False
- child.select = True
+ child.select_set(state=True)
if len(context.selected_objects) > 0:
bpy.ops.object.make_single_user(type='SELECTED_OBJECTS', object=True,
obdata=True, material=False, texture=False, animation=False)
@@ -1803,9 +1803,9 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
if 'archipack_hole' in child:
child.hide_select = True
bpy.ops.object.select_all(action="DESELECT")
- context.scene.objects.active = act
+ context.view_layer.objects.active = act
for o in sel:
- o.select = True
+ o.select_set(state=True)
# -----------------------------------------------------
# Execute
@@ -1816,8 +1816,8 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
bpy.ops.object.select_all(action="DESELECT")
o = self.create(context)
o.location = bpy.context.scene.cursor_location
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.manipulate()
elif self.mode == 'DELETE':
self.delete(context)
@@ -1831,14 +1831,14 @@ class ARCHIPACK_OT_window(ArchipackCreateTool, Operator):
return {'CANCELLED'}
-class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
+class ARCHIPACK_OT_window_draw(ArchipackDrawTool, Operator):
bl_idname = "archipack.window_draw"
bl_label = "Draw Windows"
bl_description = "Draw Windows over walls"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- filepath = StringProperty(default="")
+ filepath : StringProperty(default="")
feedback = None
stack = []
object_name = ""
@@ -1850,7 +1850,7 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def draw_callback(self, _self, context):
self.feedback.draw(context)
@@ -1862,8 +1862,8 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
if archipack_window.filter(o):
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
if event.shift:
bpy.ops.archipack.window(mode="UNIQUE")
@@ -1871,23 +1871,23 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
# instance subs
new_w = o.copy()
new_w.data = o.data
- context.scene.objects.link(new_w)
+ context.scene.collection.objects.link(new_w)
for child in o.children:
if "archipack_hole" not in child:
new_c = child.copy()
new_c.data = child.data
new_c.parent = new_w
- context.scene.objects.link(new_c)
+ context.scene.collection.objects.link(new_c)
# dup handle if any
for c in child.children:
new_h = c.copy()
new_h.data = c.data
new_h.parent = new_c
- context.scene.objects.link(new_h)
+ context.scene.collection.objects.link(new_h)
o = new_w
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
else:
bpy.ops.archipack.window(auto_manipulate=False, filepath=self.filepath)
@@ -1896,8 +1896,8 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
self.object_name = o.name
bpy.ops.archipack.generate_hole('INVOKE_DEFAULT')
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
def modal(self, context, event):
@@ -1914,14 +1914,14 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
# hide hole from raycast
if hole is not None:
- o.hide = True
- hole.hide = True
+ o.hide_viewport = True
+ hole.hide_viewport = True
- res, tM, wall, y = self.mouse_hover_wall(context, event)
+ res, tM, wall, width, y, z_offset = self.mouse_hover_wall(context, event)
if hole is not None:
- o.hide = False
- hole.hide = False
+ o.hide_viewport = False
+ hole.hide_viewport = False
if res and d is not None:
o.matrix_world = tM
@@ -1939,14 +1939,14 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
if event.type in {'LEFTMOUSE', 'RET', 'NUMPAD_ENTER', 'SPACE'}:
if wall is not None:
- context.scene.objects.active = wall
- wall.select = True
+ context.view_layer.objects.active = wall
+ wall.select_set(state=True)
if bpy.ops.archipack.single_boolean.poll():
bpy.ops.archipack.single_boolean()
- wall.select = False
+ wall.select_set(state=False)
# o must be a window here
if d is not None:
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
self.stack.append(o)
self.add_object(context, event)
context.active_object.matrix_world = tM
@@ -1960,9 +1960,9 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
):
if len(self.stack) > 0:
last = self.stack.pop()
- context.scene.objects.active = last
+ context.view_layer.objects.active = last
bpy.ops.archipack.window(mode="DELETE")
- context.scene.objects.active = o
+ context.view_layer.objects.active = o
return {'RUNNING_MODAL'}
if event.value == 'RELEASE':
@@ -1986,11 +1986,11 @@ class ARCHIPACK_OT_window_draw(ArchpackDrawTool, Operator):
# invoke with shift pressed will use current object as basis for linked copy
if self.filepath == '' and archipack_window.filter(context.active_object):
o = context.active_object
- context.scene.objects.active = None
+ context.view_layer.objects.active = None
bpy.ops.object.select_all(action="DESELECT")
if o is not None:
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
self.add_object(context, event)
self.feedback = FeedbackPanel()
self.feedback.instructions(context, "Draw a window", "Click & Drag over a wall", [
@@ -2041,19 +2041,19 @@ class ARCHIPACK_OT_window_panel(Operator):
bl_description = "Window panel"
bl_category = 'Archipack'
bl_options = {'REGISTER', 'UNDO'}
- center = FloatVectorProperty(
+ center : FloatVectorProperty(
subtype='XYZ'
)
- origin = FloatVectorProperty(
+ origin : FloatVectorProperty(
subtype='XYZ'
)
- size = FloatVectorProperty(
+ size : FloatVectorProperty(
subtype='XYZ'
)
- radius = FloatVectorProperty(
+ radius : FloatVectorProperty(
subtype='XYZ'
)
- angle_y = FloatProperty(
+ angle_y : FloatProperty(
name='angle',
unit='ROTATION',
subtype='ANGLE',
@@ -2061,25 +2061,25 @@ class ARCHIPACK_OT_window_panel(Operator):
default=0, precision=2,
description='angle'
)
- frame_y = FloatProperty(
+ frame_y : FloatProperty(
name='Depth',
min=0, max=100,
default=0.06, precision=2,
description='frame depth'
)
- frame_x = FloatProperty(
+ frame_x : FloatProperty(
name='Width',
min=0, max=100,
default=0.06, precision=2,
description='frame width'
)
- curve_steps = IntProperty(
+ curve_steps : IntProperty(
name="curve steps",
min=1,
max=128,
default=16
)
- shape = EnumProperty(
+ shape : EnumProperty(
name='Shape',
items=(
('RECTANGLE', 'Rectangle', '', 0),
@@ -2090,19 +2090,19 @@ class ARCHIPACK_OT_window_panel(Operator):
),
default='RECTANGLE'
)
- pivot = FloatProperty(
+ pivot : FloatProperty(
name='pivot',
min=-1, max=1,
default=-1, precision=2,
description='pivot'
)
- side_material = IntProperty(
+ side_material : IntProperty(
name="side material",
min=0,
max=2,
default=0
)
- handle = EnumProperty(
+ handle : EnumProperty(
name='Handle',
items=(
('NONE', 'No handle', '', 0),
@@ -2111,27 +2111,27 @@ class ARCHIPACK_OT_window_panel(Operator):
),
default='NONE'
)
- handle_model = IntProperty(
+ handle_model : IntProperty(
name="handle model",
default=1,
min=1,
max=2
)
- handle_altitude = FloatProperty(
+ handle_altitude : FloatProperty(
name='handle altitude',
min=0, max=1000,
default=0.2, precision=2,
description='handle altitude'
)
- fixed = BoolProperty(
+ fixed : BoolProperty(
name="Fixed",
default=False
)
- material = StringProperty(
+ material : StringProperty(
name="material",
default=""
)
- enable_glass = BoolProperty(
+ enable_glass : BoolProperty(
name="Enable glass",
default=True
)
@@ -2139,7 +2139,7 @@ class ARCHIPACK_OT_window_panel(Operator):
def draw(self, context):
layout = self.layout
row = layout.row()
- row.label("Use Properties panel (N) to define parms", icon='INFO')
+ row.label(text="Use Properties panel (N) to define parms", icon='INFO')
def create(self, context):
m = bpy.data.meshes.new("Window Panel")
@@ -2161,9 +2161,9 @@ class ARCHIPACK_OT_window_panel(Operator):
d.handle_model = self.handle_model
d.handle_altitude = self.handle_altitude
d.enable_glass = self.enable_glass
- context.scene.objects.link(o)
- o.select = True
- context.scene.objects.active = o
+ context.scene.collection.objects.link(o)
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
m = o.archipack_material.add()
m.category = "window"
m.material = self.material
@@ -2180,8 +2180,8 @@ class ARCHIPACK_OT_window_panel(Operator):
def execute(self, context):
if context.mode == "OBJECT":
o = self.create(context)
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
return {'FINISHED'}
else:
self.report({'WARNING'}, "Archipack: Option only valid in Object mode")
diff --git a/archipack/bmesh_utils.py b/archipack/bmesh_utils.py
index 1157d9a3..54805f7b 100644
--- a/archipack/bmesh_utils.py
+++ b/archipack/bmesh_utils.py
@@ -34,8 +34,8 @@ class BmeshEdit():
"""
private, start bmesh editing of active object
"""
- o.select = True
- context.scene.objects.active = o
+ o.select_set(state=True)
+ context.view_layer.objects.active = o
bpy.ops.object.mode_set(mode='EDIT')
bm = bmesh.from_edit_mesh(o.data)
bm.verts.ensure_lookup_table()
@@ -212,11 +212,11 @@ class BmeshEdit():
@staticmethod
def bevel(context, o,
offset,
- offset_type=0,
+ offset_type='OFFSET',
segments=1,
profile=0.5,
vertex_only=False,
- clight_overlap=True,
+ clamp_overlap=True,
material=-1,
use_selection=True):
"""
@@ -245,7 +245,7 @@ class BmeshEdit():
segments=segments,
profile=profile,
vertex_only=vertex_only,
- clight_overlap=clight_overlap,
+ clamp_overlap=clamp_overlap,
material=material)
bm.to_mesh(o.data)