Support linked collections used as input in a Geometry Nodes modifier
Add support for linked collections that are used as input in a Geometry Nodes modifier. This requires iterating over the geometry nodes modifier settings, which consists of ID properties. If such an ID property is of type `IDP_ID`, its pointer is followed and the pointed-to datablock + its library are visited. This following of pointers happens in the 'expand' phase, which was only done for linked library blend files. Since this commit, the old behaviour of simply looping over all non-`DATA` datablocks of the to-be-packed blend file is not enough, and datablock expansion is done for all local datablocks as well.
This commit is contained in:
parent
932283be65
commit
0bd18594f6
@ -3,6 +3,11 @@
|
|||||||
This file logs the changes that are actually interesting to users (new features,
|
This file logs the changes that are actually interesting to users (new features,
|
||||||
changed functionality, fixed bugs).
|
changed functionality, fixed bugs).
|
||||||
|
|
||||||
|
## Version 1.6 (in development)
|
||||||
|
|
||||||
|
- Support linked collections used as input in a Geometry Nodes modifier.
|
||||||
|
|
||||||
|
|
||||||
## Version 1.5.1 (2021-07-22)
|
## Version 1.5.1 (2021-07-22)
|
||||||
|
|
||||||
- Add log warning if SegmentationFault caused by dereferencing invalid pointer is silenced when strict_pointer_mode is turned off.
|
- Add log warning if SegmentationFault caused by dereferencing invalid pointer is silenced when strict_pointer_mode is turned off.
|
||||||
|
|||||||
@ -61,6 +61,17 @@ OB_DUPLIGROUP = 1 << 8
|
|||||||
PTCACHE_DISK_CACHE = 64
|
PTCACHE_DISK_CACHE = 64
|
||||||
PTCACHE_EXTERNAL = 512
|
PTCACHE_EXTERNAL = 512
|
||||||
|
|
||||||
|
# DNA_ID_types.h
|
||||||
|
IDP_STRING = 0
|
||||||
|
IDP_INT = 1
|
||||||
|
IDP_FLOAT = 2
|
||||||
|
IDP_ARRAY = 5
|
||||||
|
IDP_GROUP = 6
|
||||||
|
IDP_ID = 7
|
||||||
|
IDP_DOUBLE = 8
|
||||||
|
IDP_IDPARRAY = 9
|
||||||
|
IDP_NUMTYPES = 10
|
||||||
|
|
||||||
# BKE_pointcache.h
|
# BKE_pointcache.h
|
||||||
PTCACHE_FILE_PTCACHE = 0
|
PTCACHE_FILE_PTCACHE = 0
|
||||||
PTCACHE_FILE_OPENVDB = 1
|
PTCACHE_FILE_OPENVDB = 1
|
||||||
|
|||||||
@ -103,6 +103,28 @@ def _expand_generic_nodetree(block: blendfile.BlendFileBlock):
|
|||||||
yield node.get_pointer(b"id")
|
yield node.get_pointer(b"id")
|
||||||
|
|
||||||
|
|
||||||
|
def _expand_generic_idprops(block: blendfile.BlendFileBlock):
|
||||||
|
"""Yield ID datablocks and their libraries referenced from ID properties."""
|
||||||
|
|
||||||
|
# TODO(@sybren): this code is very crude, and happens to work on ID
|
||||||
|
# properties of Geometry Nodes modifiers, which is what it was written for.
|
||||||
|
# It should probably be rewritten to properly iterate over & recurse into
|
||||||
|
# all groups.
|
||||||
|
settings_props = block.get_pointer((b"settings", b"properties"))
|
||||||
|
if not settings_props:
|
||||||
|
return
|
||||||
|
|
||||||
|
subprops = settings_props.get_pointer((b"data", b"group", b"first"))
|
||||||
|
for idprop in iterators.listbase(subprops):
|
||||||
|
if idprop[b"type"] != cdefs.IDP_ID:
|
||||||
|
continue
|
||||||
|
id_datablock = idprop.get_pointer((b"data", b"pointer"))
|
||||||
|
if not id_datablock:
|
||||||
|
continue
|
||||||
|
yield id_datablock
|
||||||
|
yield id_datablock.get_pointer(b"lib")
|
||||||
|
|
||||||
|
|
||||||
def _expand_generic_nodetree_id(block: blendfile.BlendFileBlock):
|
def _expand_generic_nodetree_id(block: blendfile.BlendFileBlock):
|
||||||
block_ntree = block.get_pointer(b"nodetree", None)
|
block_ntree = block.get_pointer(b"nodetree", None)
|
||||||
if block_ntree is not None:
|
if block_ntree is not None:
|
||||||
@ -251,6 +273,7 @@ def _expand_object(block: blendfile.BlendFileBlock):
|
|||||||
# Currently only node groups are supported. If the support should expand
|
# Currently only node groups are supported. If the support should expand
|
||||||
# to more types, something more intelligent than this should be made.
|
# to more types, something more intelligent than this should be made.
|
||||||
if mod_type == cdefs.eModifierType_Nodes:
|
if mod_type == cdefs.eModifierType_Nodes:
|
||||||
|
yield from _expand_generic_idprops(block_mod)
|
||||||
yield block_mod.get_pointer(b"node_group")
|
yield block_mod.get_pointer(b"node_group")
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -110,11 +110,7 @@ class BlockIterator:
|
|||||||
self.to_visit.put(lib)
|
self.to_visit.put(lib)
|
||||||
continue
|
continue
|
||||||
|
|
||||||
if limit_to:
|
self._queue_dependencies(block)
|
||||||
# We're limiting the blocks, so we have to expand them to make
|
|
||||||
# sure we don't miss anything. Otherwise we're yielding the
|
|
||||||
# entire file anyway, and no expansion is necessary.
|
|
||||||
self._queue_dependencies(block)
|
|
||||||
self.blocks_yielded.add((bpath, block.addr_old))
|
self.blocks_yielded.add((bpath, block.addr_old))
|
||||||
yield block
|
yield block
|
||||||
|
|
||||||
@ -167,6 +163,7 @@ class BlockIterator:
|
|||||||
|
|
||||||
def _queue_dependencies(self, block: blendfile.BlendFileBlock):
|
def _queue_dependencies(self, block: blendfile.BlendFileBlock):
|
||||||
for block in expanders.expand_block(block):
|
for block in expanders.expand_block(block):
|
||||||
|
assert isinstance(block, blendfile.BlendFileBlock), "unexpected %r" % block
|
||||||
self.to_visit.put(block)
|
self.to_visit.put(block)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
BIN
tests/blendfiles/geometry-nodes-2/lib_trash.blend
Normal file
BIN
tests/blendfiles/geometry-nodes-2/lib_trash.blend
Normal file
Binary file not shown.
BIN
tests/blendfiles/geometry-nodes-2/set_file.blend
Normal file
BIN
tests/blendfiles/geometry-nodes-2/set_file.blend
Normal file
Binary file not shown.
BIN
tests/blendfiles/geometry-nodes-2/shot_file.blend
Normal file
BIN
tests/blendfiles/geometry-nodes-2/shot_file.blend
Normal file
Binary file not shown.
@ -436,6 +436,34 @@ class DepsTest(AbstractTracerTest):
|
|||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def test_geometry_nodes_modifier_input(self):
|
||||||
|
"""Test linked collection as input to geom nodes modifier.
|
||||||
|
|
||||||
|
Here a Geometry Nodes modifier references a collection that is not
|
||||||
|
instanced into the scene, which caused it to be missed.
|
||||||
|
"""
|
||||||
|
self.assert_deps(
|
||||||
|
"geometry-nodes-2/shot_file.blend",
|
||||||
|
{
|
||||||
|
b"LIset_file.blend": Expect(
|
||||||
|
type="Library",
|
||||||
|
full_field="name[1024]",
|
||||||
|
dirname_field=None,
|
||||||
|
basename_field=None,
|
||||||
|
asset_path=b"//set_file.blend",
|
||||||
|
is_sequence=False,
|
||||||
|
),
|
||||||
|
b"LIlib_trash.blend": Expect(
|
||||||
|
type="Library",
|
||||||
|
full_field="name[1024]",
|
||||||
|
dirname_field=None,
|
||||||
|
basename_field=None,
|
||||||
|
asset_path=b"//lib_trash.blend",
|
||||||
|
is_sequence=False,
|
||||||
|
),
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
def test_usage_abspath(self):
|
def test_usage_abspath(self):
|
||||||
deps = [
|
deps = [
|
||||||
dep
|
dep
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user