diff --git a/NodeToPython/compositor/operator.py b/NodeToPython/compositor/operator.py index d16ebbc..682517d 100644 --- a/NodeToPython/compositor/operator.py +++ b/NodeToPython/compositor/operator.py @@ -31,45 +31,44 @@ def __init__(self): self._used_vars[name] = 0 - def _create_scene(self, indent: str): + def _create_scene(self, indent_level: int): #TODO: wrap in more general unique name util function - self._write(f"# Generate unique scene name", indent) + self._write(f"# Generate unique scene name", indent_level) self._write(f"{BASE_NAME} = {str_to_py_str(self.compositor_name)}", - indent) - self._write(f"{END_NAME} = {BASE_NAME}", indent) - self._write(f"if bpy.data.scenes.get({END_NAME}) != None:", indent) + indent_level) + self._write(f"{END_NAME} = {BASE_NAME}", indent_level) + self._write(f"if bpy.data.scenes.get({END_NAME}) != None:", indent_level) - indent2 = f"{indent}\t" - self._write(f"{INDEX} = 1", indent2) + self._write(f"{INDEX} = 1", indent_level + 1) self._write(f"{END_NAME} = {BASE_NAME} + f\".{{i:03d}}\"", - indent2) + indent_level + 1) self._write(f"while bpy.data.scenes.get({END_NAME}) != None:", - indent2) + indent_level + 1) - indent3 = f"{indent}\t\t" - self._write(f"{END_NAME} = {BASE_NAME} + f\".{{{INDEX}:03d}}\"", indent3) - self._write(f"{INDEX} += 1\n", indent3) + self._write(f"{END_NAME} = {BASE_NAME} + f\".{{{INDEX}:03d}}\"", + indent_level + 2) + self._write(f"{INDEX} += 1\n", indent_level + 2) - self._write(f"{SCENE} = bpy.context.window.scene.copy()\n", indent) - self._write(f"{SCENE}.name = {END_NAME}", indent) - self._write(f"{SCENE}.use_fake_user = True", indent) - self._write(f"bpy.context.window.scene = {SCENE}", indent) + self._write(f"{SCENE} = bpy.context.window.scene.copy()\n", indent_level) + self._write(f"{SCENE}.name = {END_NAME}", indent_level) + self._write(f"{SCENE}.use_fake_user = True", indent_level) + self._write(f"bpy.context.window.scene = {SCENE}", indent_level) def _initialize_compositor_node_tree(self, ntp_nt, nt_name): #initialize node group - self._write(f"#initialize {nt_name} node group", self._outer) - self._write(f"def {ntp_nt.var}_node_group():", self._outer) + self._write(f"#initialize {nt_name} node group", self._outer_indent_level) + self._write(f"def {ntp_nt.var}_node_group():", self._outer_indent_level) if ntp_nt.node_tree == self._base_node_tree: self._write(f"{ntp_nt.var} = {SCENE}.node_tree") self._write(f"#start with a clean node tree") self._write(f"for {NODE} in {ntp_nt.var}.nodes:") - self._write(f"\t{ntp_nt.var}.nodes.remove({NODE})") + self._write(f"{ntp_nt.var}.nodes.remove({NODE})", self._inner_indent_level + 1) else: self._write((f"{ntp_nt.var} = bpy.data.node_groups.new(" f"type = \'CompositorNodeTree\', " f"name = {str_to_py_str(nt_name)})")) - self._write("") + self._write("", 0) # Compositor node tree settings #TODO: might be good to make this optional @@ -120,8 +119,6 @@ def _set_color_balance_settings(self, node: CompositorNodeColorBalance color_balance_info = self._node_infos['CompositorNodeColorBalance'] self._node_infos['CompositorNodeColorBalance'] = color_balance_info._replace(attributes_ = lst) - for setting in self._node_infos['CompositorNodeColorBalance'].attributes_: - print(setting.name_) def _process_node(self, node: Node, ntp_nt: NTP_NodeTree): """ @@ -191,7 +188,7 @@ def _process_node_tree(self, node_tree: CompositorNodeTree): self._write(f"return {nt_var}\n") #create node group - self._write(f"{nt_var} = {nt_var}_node_group()\n", self._outer) + self._write(f"{nt_var} = {nt_var}_node_group()\n", self._outer_indent_level) def execute(self, context): if not self._setup_options(context.scene.ntp_options): @@ -214,8 +211,8 @@ def execute(self, context): comp_var = clean_string(self.compositor_name) if self._mode == 'ADDON': - self._outer = "\t\t" - self._inner = "\t\t\t" + self._outer_indent_level = 2 + self._inner_indent_level = 3 if not self._setup_addon_directories(context, comp_var): return {'CANCELLED'} @@ -226,7 +223,7 @@ def execute(self, context): self._class_name = clean_string(self.compositor_name, lower=False) self._init_operator(comp_var, self.compositor_name) - self._write("def execute(self, context):", "\t") + self._write("def execute(self, context):", 1) else: self._file = StringIO("") if self._include_imports: @@ -234,9 +231,9 @@ def execute(self, context): if self.is_scene: if self._mode == 'ADDON': - self._create_scene("\t\t") + self._create_scene(2) elif self._mode == 'SCRIPT': - self._create_scene("") + self._create_scene(0) node_trees_to_process = self._topological_sort(self._base_node_tree) @@ -244,7 +241,7 @@ def execute(self, context): self._process_node_tree(node_tree) if self._mode == 'ADDON': - self._write("return {'FINISHED'}\n", self._outer) + self._write("return {'FINISHED'}\n", self._outer_indent_level) self._create_menu_func() self._create_register_func() diff --git a/NodeToPython/geometry/operator.py b/NodeToPython/geometry/operator.py index 4cb8a8b..5e1a7b7 100644 --- a/NodeToPython/geometry/operator.py +++ b/NodeToPython/geometry/operator.py @@ -81,7 +81,7 @@ def _process_zones(self, zone_inputs: list[GeometryNode]) -> None: #must set defaults after paired with output self._set_socket_defaults(zone_input) self._set_socket_defaults(zone_output) - self._write("") + self._write("", 0) if bpy.app.version >= (4, 0, 0): def _set_geo_tree_properties(self, node_tree: GeometryNodeTree) -> None: @@ -105,7 +105,7 @@ def _set_geo_tree_properties(self, node_tree: GeometryNodeTree) -> None: for flag in tool_flags: if hasattr(node_tree, flag) is True: self._write(f"{nt_var}.{flag} = {getattr(node_tree, flag)}") - self._write("") + self._write("", 0) def _process_node_tree(self, node_tree: GeometryNodeTree) -> None: """ @@ -119,8 +119,8 @@ def _process_node_tree(self, node_tree: GeometryNodeTree) -> None: self._node_tree_vars[node_tree] = nt_var #initialize node group - self._write(f"#initialize {nt_var} node group", self._outer) - self._write(f"def {nt_var}_node_group():", self._outer) + self._write(f"#initialize {nt_var} node group", self._outer_indent_level) + self._write(f"def {nt_var}_node_group():", self._outer_indent_level) self._write(f"{nt_var} = bpy.data.node_groups.new(" f"type = \'GeometryNodeTree\', " f"name = {str_to_py_str(node_tree.name)})\n") @@ -155,19 +155,19 @@ def _process_node_tree(self, node_tree: GeometryNodeTree) -> None: self._write(f"return {nt_var}\n") #create node group - self._write(f"{nt_var} = {nt_var}_node_group()\n", self._outer) + self._write(f"{nt_var} = {nt_var}_node_group()\n", self._outer_indent_level) def _apply_modifier(self, nt: GeometryNodeTree, nt_var: str): #get object - self._write(f"{OBJECT_NAME} = bpy.context.object.name", self._outer) - self._write(f"{OBJECT} = bpy.data.objects[{OBJECT_NAME}]", self._outer) + self._write(f"{OBJECT_NAME} = bpy.context.object.name", self._outer_indent_level) + self._write(f"{OBJECT} = bpy.data.objects[{OBJECT_NAME}]", self._outer_indent_level) #set modifier to the one we just created mod_name = str_to_py_str(nt.name) self._write(f"{MODIFIER} = obj.modifiers.new(name = {mod_name}, " - f"type = 'NODES')", self._outer) - self._write(f"{MODIFIER}.node_group = {nt_var}", self._outer) + f"type = 'NODES')", self._outer_indent_level) + self._write(f"{MODIFIER}.node_group = {nt_var}", self._outer_indent_level) def execute(self, context): @@ -181,8 +181,8 @@ def execute(self, context): nt_var = clean_string(nt.name) if self._mode == 'ADDON': - self._outer = "\t\t" - self._inner = "\t\t\t" + self._outer_indent_level = 2 + self._inner_indent_level = 3 if not self._setup_addon_directories(context, nt_var): return {'CANCELLED'} @@ -192,7 +192,7 @@ def execute(self, context): self._create_header(nt.name) self._class_name = clean_string(nt.name, lower = False) self._init_operator(nt_var, nt.name) - self._write("def execute(self, context):", "\t") + self._write("def execute(self, context):", 1) else: self._file = StringIO("") if self._include_imports: @@ -206,7 +206,7 @@ def execute(self, context): if self._mode == 'ADDON': self._apply_modifier(nt, nt_var) - self._write("return {'FINISHED'}\n", self._outer) + self._write("return {'FINISHED'}\n", self._outer_indent_level) self._create_menu_func() self._create_register_func() self._create_unregister_func() diff --git a/NodeToPython/ntp_operator.py b/NodeToPython/ntp_operator.py index babd60d..1b28435 100644 --- a/NodeToPython/ntp_operator.py +++ b/NodeToPython/ntp_operator.py @@ -79,8 +79,8 @@ def __init__(self): self._class_name: str = None # Indentation to use for the default write function - self._outer: str = "" - self._inner: str = "\t" + self._outer_indent_level: int = 0 + self._inner_indent_level: int = 1 # Base node tree we're converting self._base_node_tree: NodeTree = None @@ -106,20 +106,34 @@ def __init__(self): # Set dimensions of generated nodes self._should_set_dimensions = True + # Indentation string (default four spaces) + self._indentation = " " + if bpy.app.version >= (3, 4, 0): # Set default values for hidden sockets self._set_unavailable_defaults = False - def _write(self, string: str, indent: str = None): - if indent is None: - indent = self._inner - self._file.write(f"{indent}{string}\n") + def _write(self, string: str, indent_level: int = None): + if indent_level is None: + indent_level = self._inner_indent_level + indent_str = indent_level * self._indentation + self._file.write(f"{indent_str}{string}\n") def _setup_options(self, options: NTPOptions) -> bool: # General self._mode = options.mode self._include_group_socket_values = options.include_group_socket_values self._should_set_dimensions = options.set_dimensions + + if options.indentation_type == 'SPACES_2': + self._indentation = " " + elif options.indentation_type == 'SPACES_4': + self._indentation = " " + elif options.indentation_type == 'SPACES_8': + self._indentation = " " + elif options.indentation_type == 'TABS': + self._indentation = "\t" + if bpy.app.version >= (3, 4, 0): self._set_unavailable_defaults = options.set_unavailable_defaults @@ -179,25 +193,25 @@ def _create_header(self, name: str) -> None: name (str): name of the add-on """ - self._write("bl_info = {", "") + self._write("bl_info = {", 0) self._name = name if self._name_override and self._name_override != "": self._name = self._name_override - self._write(f"\t\"name\" : {str_to_py_str(self._name)},", "") + self._write(f"\"name\" : {str_to_py_str(self._name)},", 1) if self._description and self._description != "": - self._write(f"\t\"description\" : {str_to_py_str(self._description)}," "") - self._write(f"\t\"author\" : {str_to_py_str(self._author_name)},", "") - self._write(f"\t\"version\" : {vec3_to_py_str(self._version)},", "") - self._write(f"\t\"blender\" : {bpy.app.version},", "") - self._write(f"\t\"location\" : {str_to_py_str(self._location)},", "") + self._write(f"\"description\" : {str_to_py_str(self._description)},", 1) + self._write(f"\"author\" : {str_to_py_str(self._author_name)},", 1) + self._write(f"\"version\" : {vec3_to_py_str(self._version)},", 1) + self._write(f"\"blender\" : {bpy.app.version},", 1) + self._write(f"\"location\" : {str_to_py_str(self._location)},", 1) category = self._category if category == "Custom": category = self._custom_category - self._write(f"\t\"category\" : {str_to_py_str(category)},", "") - self._write("}\n", "") - self._write("import bpy", "") - self._write("import mathutils", "") - self._write("import os\n", "") + self._write(f"\"category\" : {str_to_py_str(category)},", 1) + self._write("}\n", 0) + self._write("import bpy", 0) + self._write("import mathutils", 0) + self._write("import os\n", 0) def _init_operator(self, idname: str, label: str) -> None: """ @@ -210,11 +224,10 @@ def _init_operator(self, idname: str, label: str) -> None: label (str): appearence inside Blender """ self._idname = idname - self._write(f"class {self._class_name}(bpy.types.Operator):", "") - self._write(f"\tbl_idname = \"node.{idname}\"", "") - self._write(f"\tbl_label = {str_to_py_str(label)}", "") - self._write("\tbl_options = {\'REGISTER\', \'UNDO\'}", "") - self._write("") + self._write(f"class {self._class_name}(bpy.types.Operator):", 0) + self._write(f"bl_idname = \"node.{idname}\"", 1) + self._write(f"bl_label = {str_to_py_str(label)}", 1) + self._write("bl_options = {\'REGISTER\', \'UNDO\'}\n", 1) def _topological_sort(self, node_tree: NodeTree) -> list[NodeTree]: """ @@ -386,12 +399,14 @@ def _set_settings_defaults(self, node: Node) -> None: self._write(f"{setting_str} = {color_to_py_str(attr)}") elif st == ST.MATERIAL: name = str_to_py_str(attr.name) - self._write((f"if {name} in bpy.data.materials:")) - self._write((f"\t{setting_str} = bpy.data.materials[{name}]")) + self._write(f"if {name} in bpy.data.materials:") + self._write(f"{setting_str} = bpy.data.materials[{name}]", + self._inner_indent_level + 1) elif st == ST.OBJECT: name = str_to_py_str(attr.name) - self._write((f"if {name} in bpy.data.objects:")) - self._write((f"\t{setting_str} = bpy.data.objects[{name}]")) + self._write(f"if {name} in bpy.data.objects:") + self._write(f"{setting_str} = bpy.data.objects[{name}]", + self._inner_indent_level + 1) elif st == ST.COLOR_RAMP: self._color_ramp_settings(node, attr_name) elif st == ST.CURVE_MAPPING: @@ -515,8 +530,8 @@ def _group_io_settings(self, node: Node, if socket_interface.hide_in_modifier is True: self._write(f"{socket_var}.hide_in_modifier = True") - self._write("") - self._write("") + self._write("", 0) + self._write("", 0) elif bpy.app.version >= (4, 0, 0): def _set_tree_socket_defaults(self, socket_interface: NodeTreeInterfaceSocket, @@ -640,7 +655,7 @@ def _create_socket(self, socket: NodeTreeInterfaceSocket, description = str_to_py_str(socket.description) self._write(f"{socket_var}.description = {description}") - self._write("") + self._write("", 0) def _create_panel(self, panel: NodeTreeInterfacePanel, panel_dict: dict[NodeTreeInterfacePanel], @@ -689,7 +704,7 @@ def _create_panel(self, panel: NodeTreeInterfacePanel, if len(panel.interface_items) > 0: self._process_items(panel, panel_dict, items_processed, ntp_nt) - self._write("") + self._write("", 0) def _process_items(self, parent: NodeTreeInterfacePanel, panel_dict: dict[NodeTreeInterfacePanel], @@ -743,7 +758,7 @@ def _tree_interface_settings(self, ntp_nt: NTP_NodeTree) -> None: self._process_items(None, panel_dict, items_processed, ntp_nt) - self._write("") + self._write("", 0) def _set_input_defaults(self, node: Node) -> None: """ @@ -819,7 +834,7 @@ def _set_input_defaults(self, node: Node) -> None: if default_val is not None: self._write(f"#{input.identifier}") self._write(f"{socket_var}.default_value = {default_val}") - self._write("") + self._write("", 0) def _set_output_defaults(self, node: Node) -> None: """ @@ -863,7 +878,8 @@ def _in_file_inputs(self, input: bpy.types.NodeSocket, socket_var: str, return name = str_to_py_str(input.default_value.name) self._write(f"if {name} in bpy.data.{type}:") - self._write(f"\t{socket_var}.default_value = bpy.data.{type}[{name}]") + self._write(f"{socket_var}.default_value = bpy.data.{type}[{name}]", + self._inner_indent_level + 1) def _set_socket_defaults(self, node: Node): """ @@ -901,7 +917,7 @@ def _color_ramp_settings(self, node: Node, color_ramp_name: str) -> None: #interpolation interpolation = enum_to_py_str(color_ramp.interpolation) self._write(f"{ramp_str}.interpolation = {interpolation}") - self._write("") + self._write("", 0) # key points self._write(f"#initialize color ramp elements") @@ -1000,8 +1016,9 @@ def _create_curve_map(self, node: Node, i: int, curve: bpy.types.CurveMap, if (node.bl_idname == 'CompositorNodeHueCorrect'): self._write(f"for {INDEX} in range" f"(len({curve_i_var}.points.values()) - 1, 1, -1):") - self._write(f"\t{curve_i_var}.points.remove(" - f"{curve_i_var}.points[{INDEX}])") + self._write(f"{curve_i_var}.points.remove(" + f"{curve_i_var}.points[{INDEX}])", + self._inner_indent_level + 1) for j, point in enumerate(curve.points): self._create_curve_map_point(j, point, curve_i_var) @@ -1096,8 +1113,8 @@ def _load_image(self, img: bpy.types.Image, img_var: str) -> None: self._write(f"{BASE_DIR} = " f"os.path.dirname(os.path.abspath(__file__))") self._write(f"{IMAGE_PATH} = " - f"os.path.join({BASE_DIR}, \"{IMAGE_DIR_NAME}\", " - f"\"{img_str}\")") + f"os.path.join({BASE_DIR}, {str_to_py_str(IMAGE_DIR_NAME)}, " + f"{str_to_py_str(img_str)})") self._write(f"{img_var} = bpy.data.images.load" f"({IMAGE_PATH}, check_existing = True)") @@ -1248,7 +1265,7 @@ def _set_parents(self, node_tree: NodeTree) -> None: node_var = self._node_vars[node] parent_var = self._node_vars[node.parent] self._write(f"{node_var}.parent = {parent_var}") - self._write("") + self._write("", 0) def _set_locations(self, node_tree: NodeTree) -> None: """ @@ -1263,7 +1280,7 @@ def _set_locations(self, node_tree: NodeTree) -> None: node_var = self._node_vars[node] self._write(f"{node_var}.location " f"= ({node.location.x}, {node.location.y})") - self._write("") + self._write("", 0) def _set_dimensions(self, node_tree: NodeTree) -> None: """ @@ -1280,7 +1297,7 @@ def _set_dimensions(self, node_tree: NodeTree) -> None: node_var = self._node_vars[node] self._write(f"{node_var}.width, {node_var}.height " f"= {node.width}, {node.height}") - self._write("") + self._write("", 0) def _init_links(self, node_tree: NodeTree) -> None: """ @@ -1358,34 +1375,31 @@ def _create_menu_func(self) -> None: """ Creates the menu function """ - self._write("def menu_func(self, context):", "") - self._write(f"self.layout.operator({self._class_name}.bl_idname)", "\t") - self._write("") + self._write("def menu_func(self, context):", 0) + self._write(f"self.layout.operator({self._class_name}.bl_idname)\n", 1) def _create_register_func(self) -> None: """ Creates the register function """ - self._write("def register():", "") - self._write(f"bpy.utils.register_class({self._class_name})", "\t") - self._write(f"bpy.types.{self._menu_id}.append(menu_func)", "\t") - self._write("") + self._write("def register():", 0) + self._write(f"bpy.utils.register_class({self._class_name})", 1) + self._write(f"bpy.types.{self._menu_id}.append(menu_func)\n", 1) def _create_unregister_func(self) -> None: """ Creates the unregister function """ - self._write("def unregister():", "") - self._write(f"bpy.utils.unregister_class({self._class_name})", "\t") - self._write(f"bpy.types.{self._menu_id}.remove(menu_func)", "\t") - self._write("") + self._write("def unregister():", 0) + self._write(f"bpy.utils.unregister_class({self._class_name})", 1) + self._write(f"bpy.types.{self._menu_id}.remove(menu_func)\n", 1) def _create_main_func(self) -> None: """ Creates the main function """ - self._write("if __name__ == \"__main__\":", "") - self._write("register()", "\t") + self._write("if __name__ == \"__main__\":", 0) + self._write("register()", 1) def _create_license(self) -> None: if not self._should_create_license: diff --git a/NodeToPython/options.py b/NodeToPython/options.py index 3ea4bff..a5df210 100644 --- a/NodeToPython/options.py +++ b/NodeToPython/options.py @@ -22,6 +22,19 @@ class NTPOptions(bpy.types.PropertyGroup): description = "Set dimensions of generated nodes", default = True ) + + indentation_type: bpy.props.EnumProperty( + name="Indentation Type", + description="Whitespace to use for each indentation block", + items = [ + ('SPACES_2', "2 Spaces", ""), + ('SPACES_4', "4 Spaces", ""), + ('SPACES_8', "8 Spaces", ""), + ('TABS', "Tabs", "") + ], + default = 'SPACES_4' + ) + if bpy.app.version >= (3, 4, 0): set_unavailable_defaults : bpy.props.BoolProperty( name = "Set unavailable defaults", @@ -92,9 +105,14 @@ class NTPOptions(bpy.types.PropertyGroup): ('SPDX:MPL-2.0', "Mozilla Public License 2.0", ""), ('SPDX:Pixar', "Pixar License", ""), ('SPDX:Zlib', "Zlib License", ""), - ('OTHER', "Other", "") + ('OTHER', "Other", "User is responsible for including the license " + "and adding it to the manifest.\n" + "Please note that by using the Blender Python " + "API your add-on must comply with the GNU GPL. " + "See https://www.blender.org/about/license/ for " + "more details") ], - default = 'OTHER' + default = 'SPDX:GPL-3.0-or-later' ) should_create_license: bpy.props.BoolProperty( name="Create License", @@ -163,7 +181,8 @@ def draw(self, context): option_list = [ "mode", "include_group_socket_values", - "set_dimensions" + "set_dimensions", + "indentation_type" ] if bpy.app.version >= (3, 4, 0): option_list.append("set_unavailable_defaults") diff --git a/NodeToPython/shader/operator.py b/NodeToPython/shader/operator.py index b614f38..5d5ff6f 100644 --- a/NodeToPython/shader/operator.py +++ b/NodeToPython/shader/operator.py @@ -27,10 +27,10 @@ def __init__(self): for name in SHADER_OP_RESERVED_NAMES: self._used_vars[name] = 0 - def _create_material(self, indent: str): + def _create_material(self, indent_level: int): self._write(f"{MAT_VAR} = bpy.data.materials.new(" - f"name = {str_to_py_str(self.material_name)})", indent) - self._write(f"{MAT_VAR}.use_nodes = True", indent) + f"name = {str_to_py_str(self.material_name)})", indent_level) + self._write(f"{MAT_VAR}.use_nodes = True", indent_level) def _initialize_shader_node_tree(self, ntp_node_tree: NTP_NodeTree, nt_name: str) -> None: @@ -42,19 +42,19 @@ def _initialize_shader_node_tree(self, ntp_node_tree: NTP_NodeTree, variable to use nt_name (str): name to use for the node tree """ - self._write(f"#initialize {nt_name} node group", self._outer) - self._write(f"def {ntp_node_tree.var}_node_group():\n", self._outer) + self._write(f"#initialize {nt_name} node group", self._outer_indent_level) + self._write(f"def {ntp_node_tree.var}_node_group():\n", self._outer_indent_level) if ntp_node_tree.node_tree == self._base_node_tree: self._write(f"{ntp_node_tree.var} = {MAT_VAR}.node_tree") self._write(f"#start with a clean node tree") self._write(f"for {NODE} in {ntp_node_tree.var}.nodes:") - self._write(f"\t{ntp_node_tree.var}.nodes.remove({NODE})") + self._write(f"{ntp_node_tree.var}.nodes.remove({NODE})", self._inner_indent_level + 1) else: self._write((f"{ntp_node_tree.var} = bpy.data.node_groups.new(" f"type = \'ShaderNodeTree\', " f"name = {str_to_py_str(nt_name)})")) - self._write("") + self._write("", 0) def _process_node(self, node: Node, ntp_nt: NTP_NodeTree) -> None: """ @@ -124,7 +124,7 @@ def _process_node_tree(self, node_tree: ShaderNodeTree) -> None: self._write(f"return {nt_var}\n") #create node group - self._write(f"{nt_var} = {nt_var}_node_group()\n", self._outer) + self._write(f"{nt_var} = {nt_var}_node_group()\n", self._outer_indent_level) def execute(self, context): @@ -142,8 +142,8 @@ def execute(self, context): mat_var = clean_string(self.material_name) if self._mode == 'ADDON': - self._outer = "\t\t" - self._inner = "\t\t\t" + self._outer_indent_level = 2 + self._inner_indent_level = 3 if not self._setup_addon_directories(context, mat_var): return {'CANCELLED'} @@ -154,16 +154,16 @@ def execute(self, context): self._class_name = clean_string(self.material_name, lower=False) self._init_operator(mat_var, self.material_name) - self._write("def execute(self, context):", "\t") + self._write("def execute(self, context):", 1) else: self._file = StringIO("") if self._include_imports: self._file.write("import bpy, mathutils\n\n") if self._mode == 'ADDON': - self._create_material("\t\t") + self._create_material(2) elif self._mode == 'SCRIPT': - self._create_material("") + self._create_material(0) node_trees_to_process = self._topological_sort(self._base_node_tree) @@ -171,7 +171,7 @@ def execute(self, context): self._process_node_tree(node_tree) if self._mode == 'ADDON': - self._write("return {'FINISHED'}", self._outer) + self._write("return {'FINISHED'}", self._outer_indent_level) self._create_menu_func() self._create_register_func() self._create_unregister_func()