feat: geometry node initial support

refactor: resolve datablocks by uuid by devault
fix: modifier texture dependencies
This commit is contained in:
Swann
2021-02-26 10:38:50 +01:00
parent 505f3ab770
commit 317fc03f87
6 changed files with 39 additions and 30 deletions

View File

@ -127,17 +127,15 @@ class BlDatablock(ReplicatedDatablock):
instance.uuid = self.uuid
def resolve(self, construct = True):
datablock_ref = None
datablock_root = getattr(bpy.data, self.bl_id)
datablock_ref = utils.find_from_attr('uuid', self.uuid, datablock_root)
if not datablock_ref:
try:
datablock_ref = datablock_root[self.data['name']]
except Exception:
pass
if not datablock_ref:
datablock_ref = utils.find_from_attr('uuid', self.uuid, datablock_root)
if construct and not datablock_ref:
name = self.data.get('name')
logging.debug(f"Constructing {name}")

View File

@ -27,7 +27,7 @@ from .dump_anything import Loader, Dumper
from .bl_datablock import BlDatablock, get_datablock_from_uuid
NODE_SOCKET_INDEX = re.compile('\[(\d*)\]')
IGNORED_SOCKETS = ['GEOMETRY']
def load_node(node_data: dict, node_tree: bpy.types.ShaderNodeTree):
""" Load a node into a node_tree from a dict
@ -52,7 +52,8 @@ def load_node(node_data: dict, node_tree: bpy.types.ShaderNodeTree):
inputs_data = node_data.get('inputs')
if inputs_data:
inputs = target_node.inputs
inputs = [i for i in target_node.inputs if i.type not in IGNORED_SOCKETS]
for idx, inpt in enumerate(inputs_data):
if idx < len(inputs) and hasattr(inputs[idx], "default_value"):
try:
@ -64,12 +65,12 @@ def load_node(node_data: dict, node_tree: bpy.types.ShaderNodeTree):
outputs_data = node_data.get('outputs')
if outputs_data:
outputs = target_node.outputs
outputs = [o for o in target_node.outputs if o.type not in IGNORED_SOCKETS]
for idx, output in enumerate(outputs_data):
if idx < len(outputs) and hasattr(outputs[idx], "default_value"):
try:
outputs[idx].default_value = output
except:
except Exception as e:
logging.warning(
f"Node {target_node.name} output {outputs[idx].name} parameter not supported, skipping ({e})")
else:
@ -206,7 +207,7 @@ def dump_node(node: bpy.types.ShaderNode) -> dict:
return dumped_node
def dump_shader_node_tree(node_tree: bpy.types.ShaderNodeTree) -> dict:
def dump_node_tree(node_tree: bpy.types.ShaderNodeTree) -> dict:
""" Dump a shader node_tree to a dict including links and nodes
:arg node_tree: dumped shader node tree
@ -276,7 +277,7 @@ def load_node_tree_sockets(sockets: bpy.types.Collection,
s['uuid'] = socket_data[2]
def load_shader_node_tree(node_tree_data: dict, target_node_tree: bpy.types.ShaderNodeTree) -> dict:
def load_node_tree(node_tree_data: dict, target_node_tree: bpy.types.ShaderNodeTree) -> dict:
"""Load a shader node_tree from dumped data
:arg node_tree_data: dumped node data
@ -387,7 +388,7 @@ class BlMaterial(BlDatablock):
if target.node_tree is None:
target.use_nodes = True
load_shader_node_tree(data['node_tree'], target.node_tree)
load_node_tree(data['node_tree'], target.node_tree)
def _dump_implementation(self, data, instance=None):
assert(instance)
@ -454,7 +455,7 @@ class BlMaterial(BlDatablock):
]
data['grease_pencil'] = gp_mat_dumper.dump(instance.grease_pencil)
elif instance.use_nodes:
data['node_tree'] = dump_shader_node_tree(instance.node_tree)
data['node_tree'] = dump_node_tree(instance.node_tree)
return data

View File

@ -21,13 +21,13 @@ import mathutils
from .dump_anything import Dumper, Loader, np_dump_collection, np_load_collection
from .bl_datablock import BlDatablock
from .bl_material import (dump_shader_node_tree,
load_shader_node_tree,
from .bl_material import (dump_node_tree,
load_node_tree,
get_node_tree_dependencies)
class BlNodeGroup(BlDatablock):
bl_id = "node_groups"
bl_class = bpy.types.ShaderNodeTree
bl_class = bpy.types.NodeTree
bl_check_common = False
bl_icon = 'NODETREE'
bl_reload_parent = False
@ -36,10 +36,10 @@ class BlNodeGroup(BlDatablock):
return bpy.data.node_groups.new(data["name"], data["type"])
def _load_implementation(self, data, target):
load_shader_node_tree(data, target)
load_node_tree(data, target)
def _dump_implementation(self, data, instance=None):
return dump_shader_node_tree(instance)
return dump_node_tree(instance)
def _resolve_deps_implementation(self):
return get_node_tree_dependencies(self.instance)

View File

@ -91,18 +91,25 @@ def _is_editmode(object: bpy.types.Object) -> bool:
child_data.is_editmode)
def find_textures_dependencies(collection):
def find_textures_dependencies(modifiers):
""" Check collection
"""
textures = []
for item in collection:
for attr in dir(item):
inst = getattr(item, attr)
if issubclass(type(inst), bpy.types.Texture) and inst is not None:
textures.append(inst)
for mod in modifiers:
modifier_attributes = [getattr(mod, attr_name) for attr_name in mod.bl_rna.properties.keys()]
for attr in modifier_attributes:
if issubclass(type(attr), bpy.types.Texture) and attr is not None:
textures.append(attr)
return textures
def find_geometry_nodes_groups(collection):
nodes_groups = []
for item in collection:
if item.type == 'NODES' and item.node_group:
nodes_groups.append(item.node_group)
return nodes_groups
def dump_vertex_groups(src_object: bpy.types.Object) -> dict:
""" Dump object's vertex groups
@ -481,5 +488,6 @@ class BlObject(BlDatablock):
if self.instance.modifiers:
deps.extend(find_textures_dependencies(self.instance.modifiers))
deps.extend(find_geometry_nodes_groups(self.instance.modifiers))
return deps

View File

@ -21,8 +21,8 @@ import mathutils
from .dump_anything import Loader, Dumper
from .bl_datablock import BlDatablock
from .bl_material import (load_shader_node_tree,
dump_shader_node_tree,
from .bl_material import (load_node_tree,
dump_node_tree,
get_node_tree_dependencies)
@ -44,7 +44,7 @@ class BlWorld(BlDatablock):
if target.node_tree is None:
target.use_nodes = True
load_shader_node_tree(data['node_tree'], target.node_tree)
load_node_tree(data['node_tree'], target.node_tree)
def _dump_implementation(self, data, instance=None):
assert(instance)
@ -58,7 +58,7 @@ class BlWorld(BlDatablock):
]
data = world_dumper.dump(instance)
if instance.use_nodes:
data['node_tree'] = dump_shader_node_tree(instance.node_tree)
data['node_tree'] = dump_node_tree(instance.node_tree)
return data

View File

@ -596,6 +596,8 @@ class Loader:
instance.write(bpy.data.textures.get(dump))
elif isinstance(rna_property_type, T.ColorRamp):
self._load_default(instance, dump)
elif isinstance(rna_property_type, T.NodeTree):
instance.write(bpy.data.node_groups.get(dump))
elif isinstance(rna_property_type, T.Object):
instance.write(bpy.data.objects.get(dump))
elif isinstance(rna_property_type, T.Mesh):