5
$\begingroup$

Let's say we have collections A and B directly under the main Scene Collection. Is it possible to move collection B inside collection A using python?

When I do this manually (drag and drop), the Info panel shows only "bpy.ops.outliner.collection_drop() ", so that didn't help.

$\endgroup$

1 Answer 1

5
$\begingroup$

Basically you just have to .unlink(collection) the sub-collection from its current parent and then .link(collection) it to the new parent collection.

Problem is there is currently no way (attribute) to get the parent collection so we need to find the parent in the first place. I'd suggest create a lookup (dict) to store the relationship and then (un)link:

import bpy

def traverse_tree(t):
    yield t
    for child in t.children:
        yield from traverse_tree(child)

def parent_lookup(coll):
    parent_lookup = {}
    for coll in traverse_tree(coll):
        for c in coll.children.keys():
            parent_lookup.setdefault(c, coll)
    return parent_lookup


C = bpy.context

# Get all collections of the scene and their parents in a dict
coll_scene = C.scene.collection
coll_parents = parent_lookup(coll_scene)

# Get collection references
coll_target = coll_scene.children.get("Collection")
active_coll = C.view_layer.active_layer_collection.collection

# Get parent of *active_coll*
active_coll_parent = coll_parents.get(active_coll.name)

if active_coll_parent:
    # Unlink *active_coll*
    active_coll_parent.children.unlink(active_coll)

    # Link *active_coll* to *coll_target*
    coll_target.children.link(active_coll)

traverse_tree(t) function from How to get all collections of the current scene?

$\endgroup$
1
  • 2
    $\begingroup$ Thank you. It works! Out of curiosity commented out the unlink() call and found that the collection got duplicated. $\endgroup$ Mar 31, 2020 at 20:39

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .