1 # SPDX-FileCopyrightText: 2018-2022 Blender Foundation
3 # SPDX-License-Identifier: GPL-2.0-or-later
8 from collections
import namedtuple
10 from bpy
.props
import (
18 ScatterSettings
= namedtuple("ScatterSettings",
19 ["seed", "density", "radius", "scale", "random_scale",
20 "rotation", "normal_offset", "use_normal_rotation"])
22 class ObjectScatterProperties(bpy
.types
.PropertyGroup
):
26 description
="Change it to get a different scatter pattern",
29 density
: FloatProperty(
34 description
="The amount of objects per unit on the line",
37 radius
: FloatProperty(
44 description
="Maximum distance of the objects to the line",
52 description
="Size of the generated objects",
55 random_scale_percentage
: FloatProperty(
56 name
="Random Scale Percentage",
62 description
="Increase to get a larger range of sizes",
65 rotation
: FloatProperty(
73 description
="Maximum rotation of the generated objects",
76 normal_offset
: FloatProperty(
81 description
="Distance from the surface",
84 use_normal_rotation
: BoolProperty(
85 name
="Use Normal Rotation",
87 description
="Rotate the instances according to the surface normals",
90 def to_settings(self
):
91 return ScatterSettings(
96 random_scale
=self
.random_scale_percentage
/ 100,
97 rotation
=self
.rotation
,
98 normal_offset
=self
.normal_offset
,
99 use_normal_rotation
=self
.use_normal_rotation
,
103 class ObjectScatterPanel(bpy
.types
.Panel
):
104 bl_idname
= "OBJECT_PT_object_scatter"
105 bl_label
= "Object Scatter"
106 bl_space_type
= 'VIEW_3D'
107 bl_region_type
= 'UI'
110 def draw(self
, context
):
112 layout
.use_property_split
= True
113 scatter
= context
.scene
.scatter_properties
115 layout
.prop(scatter
, "density", slider
=True)
116 layout
.prop(scatter
, "radius", slider
=True)
118 col
= layout
.column(align
=True)
119 col
.prop(scatter
, "scale", slider
=True)
120 col
.prop(scatter
, "random_scale_percentage", text
="Randomness", slider
=True)
122 layout
.prop(scatter
, "use_normal_rotation")
123 layout
.prop(scatter
, "rotation", slider
=True)
124 layout
.prop(scatter
, "normal_offset", text
="Offset", slider
=True)
125 layout
.prop(scatter
, "seed")
127 def draw_menu(self
, context
):
129 layout
.operator("object.scatter")
132 ObjectScatterProperties
,
138 bpy
.utils
.register_class(cls
)
139 bpy
.types
.Scene
.scatter_properties
= PointerProperty(type=ObjectScatterProperties
)
140 bpy
.types
.VIEW3D_MT_object
.append(draw_menu
)
144 bpy
.utils
.unregister_class(cls
)
145 del bpy
.types
.Scene
.scatter_properties
146 bpy
.types
.VIEW3D_MT_object
.remove(draw_menu
)