Refactor: Untangle confusing & unsafe outliner tree element data passing
The outliner tree element creation function passed a `void *idv` argument and did weird and hard to follow stuff with it (like casting it to `ID *` even though it wouldn't point to an ID, and further overriding it based on the element type). This change tries to untangle this, so that it's easy to follow what's going on, and so that a bunch of casts from non-ID data to ID pointers are removed. Basically the void pointer is split into an ID pointer for the owning ID (if any) and a void pointer for custom data for the element creation. This can be made type safe still, but that's for another commit. It also allows us to remove some wrapper structs. The element creation function itself no longer needs to know what kind of data is passed via the void pointer. So this change has a number of benefits in fact. Also improves/adds related comments. Was quite careful to not cause behavioral changes.
This commit is contained in:
@@ -295,56 +295,6 @@ struct IDsSelectedData {
|
||||
ListBase selected_array;
|
||||
};
|
||||
|
||||
struct BoneElementCreateData {
|
||||
ID *armature_id;
|
||||
Bone *bone;
|
||||
};
|
||||
|
||||
struct EditBoneElementCreateData {
|
||||
ID *armature_id;
|
||||
EditBone *ebone;
|
||||
};
|
||||
|
||||
struct ConstraintElementCreateData {
|
||||
Object *object;
|
||||
bConstraint *con;
|
||||
};
|
||||
|
||||
struct DeformGroupElementCreateData {
|
||||
Object *object;
|
||||
bDeformGroup *defgroup;
|
||||
};
|
||||
|
||||
struct GPencilEffectElementCreateData {
|
||||
Object *object;
|
||||
ShaderFxData *fx;
|
||||
};
|
||||
|
||||
struct ModifierCreateElementData {
|
||||
Object *object;
|
||||
ModifierDataStoreElem *md;
|
||||
};
|
||||
|
||||
struct ParticleSystemElementCreateData {
|
||||
Object *object;
|
||||
ParticleSystem *psys;
|
||||
};
|
||||
|
||||
struct PoseChannelElementCreateData {
|
||||
Object *object;
|
||||
bPoseChannel *pchan;
|
||||
};
|
||||
|
||||
struct PoseGroupElementCreateData {
|
||||
Object *object;
|
||||
bActionGroup *agrp;
|
||||
};
|
||||
|
||||
struct ViewLayerElementCreateData {
|
||||
Scene *scene;
|
||||
ViewLayer *view_layer;
|
||||
};
|
||||
|
||||
TreeTraversalAction outliner_collect_selected_collections(TreeElement *te, void *customdata);
|
||||
TreeTraversalAction outliner_collect_selected_objects(TreeElement *te, void *customdata);
|
||||
|
||||
|
||||
@@ -210,7 +210,8 @@ static void outliner_add_line_styles(SpaceOutliner *space_outliner,
|
||||
continue;
|
||||
}
|
||||
linestyle->id.tag &= ~LIB_TAG_DOIT;
|
||||
outliner_add_element(space_outliner, lb, linestyle, te, TSE_SOME_ID, 0);
|
||||
outliner_add_element(
|
||||
space_outliner, lb, reinterpret_cast<ID *>(linestyle), nullptr, te, TSE_SOME_ID, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -219,86 +220,46 @@ static void outliner_add_line_styles(SpaceOutliner *space_outliner,
|
||||
|
||||
TreeElement *outliner_add_element(SpaceOutliner *space_outliner,
|
||||
ListBase *lb,
|
||||
void *idv,
|
||||
ID *owner_id,
|
||||
void *create_data,
|
||||
TreeElement *parent,
|
||||
short type,
|
||||
short index,
|
||||
const bool expand)
|
||||
{
|
||||
ID *id = static_cast<ID *>(idv);
|
||||
/* Pointer to store in #TreeStoreElem.id to identify the element over rebuilds and reconstruct it
|
||||
* on file read. */
|
||||
/* FIXME: This is may be an arbitrary void pointer that is cast to an ID pointer. Could be a
|
||||
* temporary stack pointer even. Often works reliably enough at runtime, and file reading handles
|
||||
* cases where data can't be reconstructed just fine (pointer is null`ed). This is still
|
||||
* completely type unsafe and error-prone. */
|
||||
ID *persistent_dataptr = owner_id ? owner_id : static_cast<ID *>(create_data);
|
||||
|
||||
if (ELEM(type, TSE_RNA_STRUCT, TSE_RNA_PROPERTY, TSE_RNA_ARRAY_ELEM)) {
|
||||
id = ((PointerRNA *)idv)->owner_id;
|
||||
if (!id) {
|
||||
id = static_cast<ID *>(((PointerRNA *)idv)->data);
|
||||
}
|
||||
}
|
||||
else if (type == TSE_GP_LAYER) {
|
||||
/* idv is the layer itself */
|
||||
id = TREESTORE(parent)->id;
|
||||
}
|
||||
else if (type == TSE_GREASE_PENCIL_NODE) {
|
||||
/* idv is the layer itself */
|
||||
id = TREESTORE(parent)->id;
|
||||
}
|
||||
else if (ELEM(type, TSE_GENERIC_LABEL)) {
|
||||
id = nullptr;
|
||||
}
|
||||
else if (ELEM(type, TSE_LIBRARY_OVERRIDE, TSE_LIBRARY_OVERRIDE_OPERATION)) {
|
||||
id = &static_cast<TreeElementOverridesData *>(idv)->id;
|
||||
}
|
||||
else if (type == TSE_BONE) {
|
||||
id = static_cast<BoneElementCreateData *>(idv)->armature_id;
|
||||
}
|
||||
else if (type == TSE_EBONE) {
|
||||
id = static_cast<EditBoneElementCreateData *>(idv)->armature_id;
|
||||
}
|
||||
else if (type == TSE_GPENCIL_EFFECT) {
|
||||
id = &static_cast<GPencilEffectElementCreateData *>(idv)->object->id;
|
||||
}
|
||||
else if (type == TSE_DEFGROUP) {
|
||||
id = &static_cast<DeformGroupElementCreateData *>(idv)->object->id;
|
||||
}
|
||||
else if (type == TSE_LINKED_PSYS) {
|
||||
id = &static_cast<ParticleSystemElementCreateData *>(idv)->object->id;
|
||||
}
|
||||
else if (type == TSE_CONSTRAINT) {
|
||||
id = &static_cast<ConstraintElementCreateData *>(idv)->object->id;
|
||||
}
|
||||
else if (type == TSE_POSEGRP) {
|
||||
id = &static_cast<PoseGroupElementCreateData *>(idv)->object->id;
|
||||
}
|
||||
else if (type == TSE_R_LAYER) {
|
||||
id = &static_cast<ViewLayerElementCreateData *>(idv)->scene->id;
|
||||
}
|
||||
else if (type == TSE_POSE_CHANNEL) {
|
||||
id = &static_cast<PoseChannelElementCreateData *>(idv)->object->id;
|
||||
}
|
||||
else if (type == TSE_LAYER_COLLECTION) {
|
||||
id = &static_cast<LayerCollection *>(idv)->collection->id;
|
||||
}
|
||||
else if (type == TSE_MODIFIER) {
|
||||
id = &static_cast<ModifierCreateElementData *>(idv)->object->id;
|
||||
if ((owner_id == nullptr) && ELEM(type, TSE_RNA_STRUCT, TSE_RNA_PROPERTY, TSE_RNA_ARRAY_ELEM)) {
|
||||
persistent_dataptr = static_cast<ID *>(((PointerRNA *)create_data)->data);
|
||||
}
|
||||
|
||||
/* exceptions */
|
||||
if (ELEM(type, TSE_ID_BASE, TSE_GENERIC_LABEL)) {
|
||||
if (ELEM(type, TSE_ID_BASE)) {
|
||||
/* pass */
|
||||
}
|
||||
else if (id == nullptr) {
|
||||
else if (ELEM(type, TSE_GENERIC_LABEL)) {
|
||||
persistent_dataptr = nullptr;
|
||||
}
|
||||
else if (persistent_dataptr == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (type == TSE_SOME_ID) {
|
||||
/* Real ID, ensure we do not get non-outliner ID types here... */
|
||||
BLI_assert(TREESTORE_ID_TYPE(id));
|
||||
BLI_assert(TREESTORE_ID_TYPE(owner_id));
|
||||
}
|
||||
|
||||
TreeElement *te = MEM_new<TreeElement>(__func__);
|
||||
/* add to the visual tree */
|
||||
BLI_addtail(lb, te);
|
||||
/* add to the storage */
|
||||
check_persistent(space_outliner, te, id, type, index);
|
||||
check_persistent(space_outliner, te, persistent_dataptr, type, index);
|
||||
TreeStoreElem *tselem = TREESTORE(te);
|
||||
|
||||
/* if we are searching for something expand to see child elements */
|
||||
@@ -311,7 +272,7 @@ TreeElement *outliner_add_element(SpaceOutliner *space_outliner,
|
||||
|
||||
/* New inheritance based element representation. Not all element types support this yet,
|
||||
* eventually it should replace #TreeElement entirely. */
|
||||
te->abstract_element = AbstractTreeElement::create_from_type(type, *te, idv);
|
||||
te->abstract_element = AbstractTreeElement::create_from_type(type, *te, owner_id, create_data);
|
||||
if (te->abstract_element) {
|
||||
/* Element types ported to the new design are expected to have their name set at this point! */
|
||||
BLI_assert(te->name != nullptr);
|
||||
@@ -386,7 +347,7 @@ TreeElement *outliner_add_element(SpaceOutliner *space_outliner,
|
||||
|
||||
/* The new type design sets the name already, don't override that here. We need to figure out
|
||||
* how to deal with the idcode for non-TSE_SOME_ID types still. Some rely on it... */
|
||||
te->idcode = GS(id->name);
|
||||
te->idcode = GS(owner_id->name);
|
||||
}
|
||||
|
||||
if (!expand) {
|
||||
@@ -417,7 +378,8 @@ BLI_INLINE void outliner_add_collection_objects(SpaceOutliner *space_outliner,
|
||||
TreeElement *parent)
|
||||
{
|
||||
LISTBASE_FOREACH (CollectionObject *, cob, &collection->gobject) {
|
||||
outliner_add_element(space_outliner, tree, cob->ob, parent, TSE_SOME_ID, 0);
|
||||
outliner_add_element(
|
||||
space_outliner, tree, reinterpret_cast<ID *>(cob->ob), nullptr, parent, TSE_SOME_ID, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -429,7 +391,7 @@ TreeElement *outliner_add_collection_recursive(SpaceOutliner *space_outliner,
|
||||
|
||||
LISTBASE_FOREACH (CollectionChild *, child, &collection->children) {
|
||||
outliner_add_element(
|
||||
space_outliner, &ten->subtree, &child->collection->id, ten, TSE_SOME_ID, 0);
|
||||
space_outliner, &ten->subtree, &child->collection->id, nullptr, ten, TSE_SOME_ID, 0);
|
||||
}
|
||||
|
||||
if (space_outliner->outlinevis != SO_SCENES) {
|
||||
|
||||
@@ -32,7 +32,7 @@ ListBase TreeDisplayDataAPI::build_tree(const TreeSourceData &source_data)
|
||||
RNA_main_pointer_create(source_data.bmain, &mainptr);
|
||||
|
||||
TreeElement *te = outliner_add_element(
|
||||
&space_outliner_, &tree, (void *)&mainptr, nullptr, TSE_RNA_STRUCT, -1);
|
||||
&space_outliner_, &tree, nullptr, (void *)&mainptr, nullptr, TSE_RNA_STRUCT, -1);
|
||||
|
||||
/* On first view open parent data elements */
|
||||
const int show_opened = !space_outliner_.treestore ||
|
||||
|
||||
@@ -137,10 +137,17 @@ TreeElement *TreeDisplayLibraries::add_library_contents(Main &mainvar, ListBase
|
||||
if (!tenlib) {
|
||||
/* Create library tree element on demand, depending if there are any data-blocks. */
|
||||
if (lib) {
|
||||
tenlib = outliner_add_element(&space_outliner_, &lb, lib, nullptr, TSE_SOME_ID, 0);
|
||||
tenlib = outliner_add_element(&space_outliner_,
|
||||
&lb,
|
||||
reinterpret_cast<ID *>(lib),
|
||||
nullptr,
|
||||
nullptr,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
}
|
||||
else {
|
||||
tenlib = outliner_add_element(&space_outliner_, &lb, &mainvar, nullptr, TSE_ID_BASE, 0);
|
||||
tenlib = outliner_add_element(
|
||||
&space_outliner_, &lb, nullptr, &mainvar, nullptr, TSE_ID_BASE, 0);
|
||||
tenlib->name = IFACE_("Current File");
|
||||
}
|
||||
}
|
||||
@@ -153,15 +160,21 @@ TreeElement *TreeDisplayLibraries::add_library_contents(Main &mainvar, ListBase
|
||||
ten = tenlib;
|
||||
}
|
||||
else {
|
||||
ten = outliner_add_element(
|
||||
&space_outliner_, &tenlib->subtree, lib, nullptr, TSE_ID_BASE, a);
|
||||
ten = outliner_add_element(&space_outliner_,
|
||||
&tenlib->subtree,
|
||||
reinterpret_cast<ID *>(lib),
|
||||
nullptr,
|
||||
nullptr,
|
||||
TSE_ID_BASE,
|
||||
a);
|
||||
ten->directdata = lbarray[a];
|
||||
ten->name = outliner_idcode_to_plural(GS(id->name));
|
||||
}
|
||||
|
||||
for (ID *id : List<ID>(lbarray[a])) {
|
||||
if (library_id_filter_poll(lib, id)) {
|
||||
outliner_add_element(&space_outliner_, &ten->subtree, id, ten, TSE_SOME_ID, 0);
|
||||
outliner_add_element(
|
||||
&space_outliner_, &ten->subtree, id, nullptr, ten, TSE_SOME_ID, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -58,7 +58,8 @@ ListBase TreeDisplayIDOrphans::build_tree(const TreeSourceData &source_data)
|
||||
TreeElement *te = nullptr;
|
||||
if (!filter_id_type) {
|
||||
ID *id = (ID *)lbarray[a]->first;
|
||||
te = outliner_add_element(&space_outliner_, &tree, lbarray[a], nullptr, TSE_ID_BASE, 0);
|
||||
te = outliner_add_element(
|
||||
&space_outliner_, &tree, nullptr, lbarray[a], nullptr, TSE_ID_BASE, 0);
|
||||
te->directdata = lbarray[a];
|
||||
te->name = outliner_idcode_to_plural(GS(id->name));
|
||||
}
|
||||
@@ -67,7 +68,7 @@ ListBase TreeDisplayIDOrphans::build_tree(const TreeSourceData &source_data)
|
||||
for (ID *id : List<ID>(lbarray[a])) {
|
||||
if (ID_REAL_USERS(id) <= 0) {
|
||||
outliner_add_element(
|
||||
&space_outliner_, (te) ? &te->subtree : &tree, id, te, TSE_SOME_ID, 0);
|
||||
&space_outliner_, (te) ? &te->subtree : &tree, id, nullptr, te, TSE_SOME_ID, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -41,7 +41,7 @@ ListBase TreeDisplayOverrideLibraryHierarchies::build_tree(const TreeSourceData
|
||||
|
||||
/* First step: Build "Current File" hierarchy. */
|
||||
TreeElement *current_file_te = outliner_add_element(
|
||||
&space_outliner_, &tree, source_data.bmain, nullptr, TSE_ID_BASE, -1);
|
||||
&space_outliner_, &tree, nullptr, source_data.bmain, nullptr, TSE_ID_BASE, -1);
|
||||
current_file_te->name = IFACE_("Current File");
|
||||
AbstractTreeElement::uncollapse_by_default(current_file_te);
|
||||
{
|
||||
@@ -49,8 +49,13 @@ ListBase TreeDisplayOverrideLibraryHierarchies::build_tree(const TreeSourceData
|
||||
|
||||
/* Add dummy child if there's nothing to display. */
|
||||
if (BLI_listbase_is_empty(¤t_file_te->subtree)) {
|
||||
TreeElement *dummy_te = outliner_add_element(
|
||||
&space_outliner_, ¤t_file_te->subtree, nullptr, current_file_te, TSE_ID_BASE, 0);
|
||||
TreeElement *dummy_te = outliner_add_element(&space_outliner_,
|
||||
¤t_file_te->subtree,
|
||||
nullptr,
|
||||
nullptr,
|
||||
current_file_te,
|
||||
TSE_ID_BASE,
|
||||
0);
|
||||
dummy_te->name = IFACE_("No Library Overrides");
|
||||
}
|
||||
}
|
||||
@@ -60,7 +65,7 @@ ListBase TreeDisplayOverrideLibraryHierarchies::build_tree(const TreeSourceData
|
||||
lib = (Library *)lib->id.next)
|
||||
{
|
||||
TreeElement *tenlib = outliner_add_element(
|
||||
&space_outliner_, &tree, lib, nullptr, TSE_SOME_ID, 0);
|
||||
&space_outliner_, &tree, reinterpret_cast<ID *>(lib), nullptr, nullptr, TSE_SOME_ID, 0);
|
||||
build_hierarchy_for_lib_or_main(source_data.bmain, *tenlib, lib);
|
||||
}
|
||||
|
||||
@@ -146,7 +151,8 @@ ListBase TreeDisplayOverrideLibraryHierarchies::build_hierarchy_for_lib_or_main(
|
||||
TreeElement *new_base_te = id_base_te_map.lookup_or_add_cb(GS(iter_id->name), [&]() {
|
||||
TreeElement *new_te = outliner_add_element(&space_outliner_,
|
||||
&parent_te.subtree,
|
||||
lib ? (void *)lib : bmain,
|
||||
reinterpret_cast<ID *>(lib),
|
||||
bmain,
|
||||
&parent_te,
|
||||
TSE_ID_BASE,
|
||||
base_index++);
|
||||
@@ -154,8 +160,14 @@ ListBase TreeDisplayOverrideLibraryHierarchies::build_hierarchy_for_lib_or_main(
|
||||
return new_te;
|
||||
});
|
||||
|
||||
TreeElement *new_id_te = outliner_add_element(
|
||||
&space_outliner_, &new_base_te->subtree, iter_id, new_base_te, TSE_SOME_ID, 0, false);
|
||||
TreeElement *new_id_te = outliner_add_element(&space_outliner_,
|
||||
&new_base_te->subtree,
|
||||
iter_id,
|
||||
nullptr,
|
||||
new_base_te,
|
||||
TSE_SOME_ID,
|
||||
0,
|
||||
false);
|
||||
|
||||
builder.build_hierarchy_for_ID(*iter_id, *new_id_te);
|
||||
}
|
||||
@@ -222,8 +234,14 @@ void OverrideIDHierarchyBuilder::build_hierarchy_for_ID_recursive(const ID &pare
|
||||
return FOREACH_BREAK;
|
||||
}
|
||||
|
||||
TreeElement *new_te = outliner_add_element(
|
||||
&space_outliner_, &te_to_expand.subtree, &id, &te_to_expand, TSE_SOME_ID, 0, false);
|
||||
TreeElement *new_te = outliner_add_element(&space_outliner_,
|
||||
&te_to_expand.subtree,
|
||||
&id,
|
||||
nullptr,
|
||||
&te_to_expand,
|
||||
TSE_SOME_ID,
|
||||
0,
|
||||
false);
|
||||
|
||||
build_data.sibling_ids.add(&id);
|
||||
|
||||
|
||||
@@ -88,7 +88,7 @@ ListBase TreeDisplayOverrideLibraryProperties::add_library_contents(Main &mainva
|
||||
|
||||
if (!filter_id_type) {
|
||||
id_base_te = outliner_add_element(
|
||||
&space_outliner_, &tree, lbarray[a], nullptr, TSE_ID_BASE, 0);
|
||||
&space_outliner_, &tree, nullptr, lbarray[a], nullptr, TSE_ID_BASE, 0);
|
||||
id_base_te->directdata = lbarray[a];
|
||||
id_base_te->name = outliner_idcode_to_plural(GS(id->name));
|
||||
|
||||
@@ -98,7 +98,7 @@ ListBase TreeDisplayOverrideLibraryProperties::add_library_contents(Main &mainva
|
||||
for (ID *id : List<ID>(lbarray[a])) {
|
||||
if (ID_IS_OVERRIDE_LIBRARY_REAL(id) && !ID_IS_LINKED(id)) {
|
||||
TreeElement *override_tree_element = outliner_add_element(
|
||||
&space_outliner_, lb_to_expand, id, id_base_te, TSE_LIBRARY_OVERRIDE_BASE, 0);
|
||||
&space_outliner_, lb_to_expand, id, nullptr, id_base_te, TSE_LIBRARY_OVERRIDE_BASE, 0);
|
||||
|
||||
if (BLI_listbase_is_empty(&override_tree_element->subtree)) {
|
||||
outliner_free_tree_element(override_tree_element, lb_to_expand);
|
||||
|
||||
@@ -43,7 +43,7 @@ ListBase TreeDisplayScenes::build_tree(const TreeSourceData &source_data)
|
||||
for (ID *id : List<ID>(source_data.bmain->scenes)) {
|
||||
Scene *scene = reinterpret_cast<Scene *>(id);
|
||||
TreeElement *te = outliner_add_element(
|
||||
&space_outliner_, &tree, scene, nullptr, TSE_SOME_ID, 0);
|
||||
&space_outliner_, &tree, reinterpret_cast<ID *>(scene), nullptr, nullptr, TSE_SOME_ID, 0);
|
||||
TreeStoreElem *tselem = TREESTORE(te);
|
||||
|
||||
/* New scene elements open by default */
|
||||
|
||||
@@ -42,11 +42,11 @@ ListBase TreeDisplaySequencer::build_tree(const TreeSourceData &source_data)
|
||||
for (Sequence *seq : List<Sequence>(ed->seqbasep)) {
|
||||
SequenceAddOp op = need_add_seq_dup(seq);
|
||||
if (op == SEQUENCE_DUPLICATE_NONE) {
|
||||
outliner_add_element(&space_outliner_, &tree, seq, nullptr, TSE_SEQUENCE, 0);
|
||||
outliner_add_element(&space_outliner_, &tree, nullptr, seq, nullptr, TSE_SEQUENCE, 0);
|
||||
}
|
||||
else if (op == SEQUENCE_DUPLICATE_ADD) {
|
||||
TreeElement *te = outliner_add_element(
|
||||
&space_outliner_, &tree, seq, nullptr, TSE_SEQUENCE_DUP, 0);
|
||||
&space_outliner_, &tree, nullptr, seq, nullptr, TSE_SEQUENCE_DUP, 0);
|
||||
add_seq_dup(seq, te, 0);
|
||||
}
|
||||
}
|
||||
@@ -103,7 +103,8 @@ void TreeDisplaySequencer::add_seq_dup(Sequence *seq, TreeElement *te, short ind
|
||||
}
|
||||
|
||||
if (STREQ(p->strip->stripdata->filename, seq->strip->stripdata->filename)) {
|
||||
outliner_add_element(&space_outliner_, &te->subtree, (void *)p, te, TSE_SEQUENCE, index);
|
||||
outliner_add_element(
|
||||
&space_outliner_, &te->subtree, nullptr, (void *)p, te, TSE_SEQUENCE, index);
|
||||
}
|
||||
p = p->next;
|
||||
}
|
||||
|
||||
@@ -80,9 +80,13 @@ ListBase TreeDisplayViewLayer::build_tree(const TreeSourceData &source_data)
|
||||
add_view_layer(*scene, tree, (TreeElement *)nullptr);
|
||||
}
|
||||
else {
|
||||
ViewLayerElementCreateData view_layer_data = {scene, view_layer};
|
||||
TreeElement &te_view_layer = *outliner_add_element(
|
||||
&space_outliner_, &tree, &view_layer_data, nullptr, TSE_R_LAYER, 0);
|
||||
TreeElement &te_view_layer = *outliner_add_element(&space_outliner_,
|
||||
&tree,
|
||||
reinterpret_cast<ID *>(scene),
|
||||
&view_layer,
|
||||
nullptr,
|
||||
TSE_R_LAYER,
|
||||
0);
|
||||
|
||||
TreeStoreElem *tselem = TREESTORE(&te_view_layer);
|
||||
|
||||
@@ -108,8 +112,13 @@ void TreeDisplayViewLayer::add_view_layer(Scene &scene, ListBase &tree, TreeElem
|
||||
/* Show objects in the view layer. */
|
||||
BKE_view_layer_synced_ensure(&scene, view_layer_);
|
||||
for (Base *base : List<Base>(*BKE_view_layer_object_bases_get(view_layer_))) {
|
||||
TreeElement *te_object = outliner_add_element(
|
||||
&space_outliner_, &tree, base->object, parent, TSE_SOME_ID, 0);
|
||||
TreeElement *te_object = outliner_add_element(&space_outliner_,
|
||||
&tree,
|
||||
reinterpret_cast<ID *>(base->object),
|
||||
nullptr,
|
||||
parent,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
te_object->directdata = base;
|
||||
}
|
||||
|
||||
@@ -120,7 +129,7 @@ void TreeDisplayViewLayer::add_view_layer(Scene &scene, ListBase &tree, TreeElem
|
||||
else {
|
||||
/* Show collections in the view layer. */
|
||||
TreeElement &ten = *outliner_add_element(
|
||||
&space_outliner_, &tree, &scene, parent, TSE_VIEW_COLLECTION_BASE, 0);
|
||||
&space_outliner_, &tree, &scene.id, nullptr, parent, TSE_VIEW_COLLECTION_BASE, 0);
|
||||
TREESTORE(&ten)->flag &= ~TSE_CLOSED;
|
||||
|
||||
/* First layer collection is for master collection, don't show it. */
|
||||
@@ -153,7 +162,7 @@ void TreeDisplayViewLayer::add_layer_collections_recursive(ListBase &tree,
|
||||
else {
|
||||
ID *id = &lc->collection->id;
|
||||
ten = outliner_add_element(
|
||||
&space_outliner_, &tree, lc, &parent_ten, TSE_LAYER_COLLECTION, 0);
|
||||
&space_outliner_, &tree, id, lc, &parent_ten, TSE_LAYER_COLLECTION, 0);
|
||||
|
||||
/* Open by default, except linked collections, which may contain many elements. */
|
||||
TreeStoreElem *tselem = TREESTORE(ten);
|
||||
@@ -176,8 +185,13 @@ void TreeDisplayViewLayer::add_layer_collection_objects(ListBase &tree,
|
||||
BKE_view_layer_synced_ensure(scene_, view_layer_);
|
||||
for (CollectionObject *cob : List<CollectionObject>(lc.collection->gobject)) {
|
||||
Base *base = BKE_view_layer_base_find(view_layer_, cob->ob);
|
||||
TreeElement *te_object = outliner_add_element(
|
||||
&space_outliner_, &tree, base->object, &ten, TSE_SOME_ID, 0);
|
||||
TreeElement *te_object = outliner_add_element(&space_outliner_,
|
||||
&tree,
|
||||
reinterpret_cast<ID *>(base->object),
|
||||
nullptr,
|
||||
&ten,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
te_object->directdata = base;
|
||||
}
|
||||
}
|
||||
@@ -281,7 +295,8 @@ void ObjectsChildrenBuilder::make_object_parent_hierarchy_collections()
|
||||
* We don't expand its sub-tree though, to make it less prominent. */
|
||||
TreeElement *child_ob_tree_element = outliner_add_element(&outliner_,
|
||||
&parent_ob_tree_element->subtree,
|
||||
child,
|
||||
reinterpret_cast<ID *>(child),
|
||||
nullptr,
|
||||
parent_ob_tree_element,
|
||||
TSE_SOME_ID,
|
||||
0,
|
||||
|
||||
@@ -51,16 +51,18 @@ namespace blender::ed::outliner {
|
||||
|
||||
std::unique_ptr<AbstractTreeElement> AbstractTreeElement::create_from_type(const int type,
|
||||
TreeElement &legacy_te,
|
||||
void *idv)
|
||||
ID *owner_id,
|
||||
void *create_data)
|
||||
{
|
||||
if (idv == nullptr) {
|
||||
if (owner_id == nullptr && create_data == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
/*
|
||||
* The following calls make an implicit assumption about what data was passed to the `idv`
|
||||
* argument of #outliner_add_element(). The old code does this already, here we just centralize
|
||||
* it as much as possible for now. Would be nice to entirely get rid of that, no more `void *`.
|
||||
* The following calls make an implicit assumption about what data was passed to the
|
||||
* `create_data` argument of #outliner_add_element(). The old code does this already, here we
|
||||
* just centralize it as much as possible for now. Would be nice to entirely get rid of that, no
|
||||
* more `void *`.
|
||||
*
|
||||
* Once #outliner_add_element() is sufficiently simplified, it should be replaced by a C++ call.
|
||||
* It could take the derived type as template parameter (e.g. #TreeElementAnimData) and use C++
|
||||
@@ -71,126 +73,131 @@ std::unique_ptr<AbstractTreeElement> AbstractTreeElement::create_from_type(const
|
||||
|
||||
switch (type) {
|
||||
case TSE_SOME_ID:
|
||||
return TreeElementID::create_from_id(legacy_te, *static_cast<ID *>(idv));
|
||||
return TreeElementID::create_from_id(legacy_te, *owner_id);
|
||||
case TSE_GENERIC_LABEL:
|
||||
return std::make_unique<TreeElementLabel>(legacy_te, static_cast<const char *>(idv));
|
||||
return std::make_unique<TreeElementLabel>(legacy_te, static_cast<const char *>(create_data));
|
||||
case TSE_ANIM_DATA:
|
||||
return std::make_unique<TreeElementAnimData>(legacy_te,
|
||||
*static_cast<IdAdtTemplate *>(idv)->adt);
|
||||
*static_cast<AnimData *>(create_data));
|
||||
case TSE_DRIVER_BASE:
|
||||
return std::make_unique<TreeElementDriverBase>(legacy_te, *static_cast<AnimData *>(idv));
|
||||
return std::make_unique<TreeElementDriverBase>(legacy_te,
|
||||
*static_cast<AnimData *>(create_data));
|
||||
case TSE_NLA:
|
||||
return std::make_unique<TreeElementNLA>(legacy_te, *static_cast<AnimData *>(idv));
|
||||
return std::make_unique<TreeElementNLA>(legacy_te, *static_cast<AnimData *>(create_data));
|
||||
case TSE_NLA_TRACK:
|
||||
return std::make_unique<TreeElementNLATrack>(legacy_te, *static_cast<NlaTrack *>(idv));
|
||||
return std::make_unique<TreeElementNLATrack>(legacy_te,
|
||||
*static_cast<NlaTrack *>(create_data));
|
||||
case TSE_NLA_ACTION:
|
||||
return std::make_unique<TreeElementNLAAction>(legacy_te, *static_cast<bAction *>(idv));
|
||||
return std::make_unique<TreeElementNLAAction>(legacy_te,
|
||||
*reinterpret_cast<bAction *>(owner_id));
|
||||
case TSE_GP_LAYER:
|
||||
return std::make_unique<TreeElementGPencilLayer>(legacy_te, *static_cast<bGPDlayer *>(idv));
|
||||
return std::make_unique<TreeElementGPencilLayer>(legacy_te,
|
||||
*static_cast<bGPDlayer *>(create_data));
|
||||
case TSE_GREASE_PENCIL_NODE:
|
||||
return std::make_unique<TreeElementGreasePencilNode>(
|
||||
legacy_te, *static_cast<bke::greasepencil::TreeNode *>(idv));
|
||||
legacy_te,
|
||||
*reinterpret_cast<GreasePencil *>(owner_id),
|
||||
*static_cast<bke::greasepencil::TreeNode *>(create_data));
|
||||
case TSE_R_LAYER_BASE:
|
||||
return std::make_unique<TreeElementViewLayerBase>(legacy_te, *static_cast<Scene *>(idv));
|
||||
case TSE_R_LAYER: {
|
||||
ViewLayerElementCreateData *view_layer_data = static_cast<ViewLayerElementCreateData *>(idv);
|
||||
return std::make_unique<TreeElementViewLayerBase>(legacy_te,
|
||||
*reinterpret_cast<Scene *>(owner_id));
|
||||
case TSE_R_LAYER:
|
||||
return std::make_unique<TreeElementViewLayer>(
|
||||
legacy_te, *view_layer_data->scene, *view_layer_data->view_layer);
|
||||
}
|
||||
legacy_te, *reinterpret_cast<Scene *>(owner_id), *static_cast<ViewLayer *>(create_data));
|
||||
case TSE_SCENE_COLLECTION_BASE:
|
||||
return std::make_unique<TreeElementCollectionBase>(legacy_te, *static_cast<Scene *>(idv));
|
||||
return std::make_unique<TreeElementCollectionBase>(legacy_te,
|
||||
*reinterpret_cast<Scene *>(owner_id));
|
||||
case TSE_SCENE_OBJECTS_BASE:
|
||||
return std::make_unique<TreeElementSceneObjectsBase>(legacy_te, *static_cast<Scene *>(idv));
|
||||
return std::make_unique<TreeElementSceneObjectsBase>(legacy_te,
|
||||
*reinterpret_cast<Scene *>(owner_id));
|
||||
case TSE_LIBRARY_OVERRIDE_BASE:
|
||||
return std::make_unique<TreeElementOverridesBase>(legacy_te, *static_cast<ID *>(idv));
|
||||
return std::make_unique<TreeElementOverridesBase>(legacy_te, *owner_id);
|
||||
case TSE_LIBRARY_OVERRIDE:
|
||||
return std::make_unique<TreeElementOverridesProperty>(
|
||||
legacy_te, *static_cast<TreeElementOverridesData *>(idv));
|
||||
legacy_te, *static_cast<TreeElementOverridesData *>(create_data));
|
||||
case TSE_LIBRARY_OVERRIDE_OPERATION:
|
||||
return std::make_unique<TreeElementOverridesPropertyOperation>(
|
||||
legacy_te, *static_cast<TreeElementOverridesData *>(idv));
|
||||
legacy_te, *static_cast<TreeElementOverridesData *>(create_data));
|
||||
case TSE_RNA_STRUCT:
|
||||
return std::make_unique<TreeElementRNAStruct>(legacy_te, *static_cast<PointerRNA *>(idv));
|
||||
return std::make_unique<TreeElementRNAStruct>(legacy_te,
|
||||
*static_cast<PointerRNA *>(create_data));
|
||||
case TSE_RNA_PROPERTY:
|
||||
return std::make_unique<TreeElementRNAProperty>(
|
||||
legacy_te, *static_cast<PointerRNA *>(idv), legacy_te.index);
|
||||
legacy_te, *static_cast<PointerRNA *>(create_data), legacy_te.index);
|
||||
case TSE_RNA_ARRAY_ELEM:
|
||||
return std::make_unique<TreeElementRNAArrayElement>(
|
||||
legacy_te, *static_cast<PointerRNA *>(idv), legacy_te.index);
|
||||
legacy_te, *static_cast<PointerRNA *>(create_data), legacy_te.index);
|
||||
case TSE_SEQUENCE:
|
||||
return std::make_unique<TreeElementSequence>(legacy_te, *static_cast<Sequence *>(idv));
|
||||
return std::make_unique<TreeElementSequence>(legacy_te,
|
||||
*static_cast<Sequence *>(create_data));
|
||||
case TSE_SEQ_STRIP:
|
||||
return std::make_unique<TreeElementSequenceStrip>(legacy_te, *static_cast<Strip *>(idv));
|
||||
return std::make_unique<TreeElementSequenceStrip>(legacy_te,
|
||||
*static_cast<Strip *>(create_data));
|
||||
case TSE_SEQUENCE_DUP:
|
||||
return std::make_unique<TreeElementSequenceStripDuplicate>(legacy_te,
|
||||
*static_cast<Sequence *>(idv));
|
||||
case TSE_BONE: {
|
||||
BoneElementCreateData *bone_data = static_cast<BoneElementCreateData *>(idv);
|
||||
return std::make_unique<TreeElementSequenceStripDuplicate>(
|
||||
legacy_te, *static_cast<Sequence *>(create_data));
|
||||
case TSE_BONE:
|
||||
return std::make_unique<TreeElementBone>(
|
||||
legacy_te, *bone_data->armature_id, *bone_data->bone);
|
||||
}
|
||||
case TSE_EBONE: {
|
||||
EditBoneElementCreateData *ebone_data = static_cast<EditBoneElementCreateData *>(idv);
|
||||
legacy_te, *owner_id, *static_cast<Bone *>(create_data));
|
||||
case TSE_EBONE:
|
||||
return std::make_unique<TreeElementEditBone>(
|
||||
legacy_te, *ebone_data->armature_id, *ebone_data->ebone);
|
||||
}
|
||||
case TSE_GPENCIL_EFFECT: {
|
||||
GPencilEffectElementCreateData *gp_effect_data =
|
||||
static_cast<GPencilEffectElementCreateData *>(idv);
|
||||
return std::make_unique<TreeElementGPencilEffect>(
|
||||
legacy_te, *gp_effect_data->object, *gp_effect_data->fx);
|
||||
}
|
||||
legacy_te, *owner_id, *static_cast<EditBone *>(create_data));
|
||||
case TSE_GPENCIL_EFFECT:
|
||||
return std::make_unique<TreeElementGPencilEffect>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<ShaderFxData *>(create_data));
|
||||
case TSE_GPENCIL_EFFECT_BASE:
|
||||
return std::make_unique<TreeElementGPencilEffectBase>(legacy_te,
|
||||
*static_cast<Object *>(idv));
|
||||
*reinterpret_cast<Object *>(owner_id));
|
||||
case TSE_DEFGROUP_BASE:
|
||||
return std::make_unique<TreeElementDeformGroupBase>(legacy_te, *static_cast<Object *>(idv));
|
||||
case TSE_DEFGROUP: {
|
||||
DeformGroupElementCreateData *defgroup_data = static_cast<DeformGroupElementCreateData *>(
|
||||
idv);
|
||||
return std::make_unique<TreeElementDeformGroup>(
|
||||
legacy_te, *defgroup_data->object, *defgroup_data->defgroup);
|
||||
}
|
||||
case TSE_LINKED_PSYS: {
|
||||
ParticleSystemElementCreateData *psys_data = static_cast<ParticleSystemElementCreateData *>(
|
||||
idv);
|
||||
return std::make_unique<TreeElementDeformGroupBase>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id));
|
||||
case TSE_DEFGROUP:
|
||||
return std::make_unique<TreeElementDeformGroup>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<bDeformGroup *>(create_data));
|
||||
case TSE_LINKED_PSYS:
|
||||
return std::make_unique<TreeElementParticleSystem>(
|
||||
legacy_te, *psys_data->object, *psys_data->psys);
|
||||
}
|
||||
legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<ParticleSystem *>(create_data));
|
||||
case TSE_CONSTRAINT_BASE:
|
||||
return std::make_unique<TreeElementConstraintBase>(legacy_te, *static_cast<Object *>(idv));
|
||||
case TSE_CONSTRAINT: {
|
||||
ConstraintElementCreateData *con_data = static_cast<ConstraintElementCreateData *>(idv);
|
||||
return std::make_unique<TreeElementConstraint>(legacy_te, *con_data->object, *con_data->con);
|
||||
}
|
||||
return std::make_unique<TreeElementConstraintBase>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id));
|
||||
case TSE_CONSTRAINT:
|
||||
return std::make_unique<TreeElementConstraint>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<bConstraint *>(create_data));
|
||||
case TSE_POSE_BASE:
|
||||
return std::make_unique<TreeElementPoseBase>(legacy_te, *static_cast<Object *>(idv));
|
||||
case TSE_POSE_CHANNEL: {
|
||||
PoseChannelElementCreateData *pchan_data = static_cast<PoseChannelElementCreateData *>(idv);
|
||||
return std::make_unique<TreeElementPoseChannel>(
|
||||
legacy_te, *pchan_data->object, *pchan_data->pchan);
|
||||
}
|
||||
return std::make_unique<TreeElementPoseBase>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id));
|
||||
case TSE_POSE_CHANNEL:
|
||||
return std::make_unique<TreeElementPoseChannel>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<bPoseChannel *>(create_data));
|
||||
case TSE_POSEGRP_BASE:
|
||||
return std::make_unique<TreeElementPoseGroupBase>(legacy_te, *static_cast<Object *>(idv));
|
||||
case TSE_POSEGRP: {
|
||||
PoseGroupElementCreateData *posegrp_data = static_cast<PoseGroupElementCreateData *>(idv);
|
||||
return std::make_unique<TreeElementPoseGroup>(
|
||||
legacy_te, *posegrp_data->object, *posegrp_data->agrp);
|
||||
}
|
||||
return std::make_unique<TreeElementPoseGroupBase>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id));
|
||||
case TSE_POSEGRP:
|
||||
return std::make_unique<TreeElementPoseGroup>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<bActionGroup *>(create_data));
|
||||
case TSE_MODIFIER_BASE:
|
||||
return std::make_unique<TreeElementModifierBase>(legacy_te, *static_cast<Object *>(idv));
|
||||
case TSE_MODIFIER: {
|
||||
ModifierCreateElementData *md_data = static_cast<ModifierCreateElementData *>(idv);
|
||||
return std::make_unique<TreeElementModifier>(legacy_te, *md_data->object, *md_data->md);
|
||||
}
|
||||
return std::make_unique<TreeElementModifierBase>(legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id));
|
||||
case TSE_MODIFIER:
|
||||
return std::make_unique<TreeElementModifier>(
|
||||
legacy_te,
|
||||
*reinterpret_cast<Object *>(owner_id),
|
||||
*static_cast<ModifierDataStoreElem *>(create_data));
|
||||
case TSE_LINKED_OB:
|
||||
return std::make_unique<TreeElementLinkedObject>(legacy_te, *static_cast<ID *>(idv));
|
||||
return std::make_unique<TreeElementLinkedObject>(legacy_te, *owner_id);
|
||||
case TSE_VIEW_COLLECTION_BASE:
|
||||
return std::make_unique<TreeElementViewCollectionBase>(legacy_te,
|
||||
*static_cast<Scene *>(idv));
|
||||
*reinterpret_cast<Scene *>(owner_id));
|
||||
case TSE_LAYER_COLLECTION:
|
||||
return std::make_unique<TreeElementLayerCollection>(legacy_te,
|
||||
*static_cast<LayerCollection *>(idv));
|
||||
return std::make_unique<TreeElementLayerCollection>(
|
||||
legacy_te, *static_cast<LayerCollection *>(create_data));
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
#include "BLI_string_ref.hh"
|
||||
#include "UI_resources.hh"
|
||||
|
||||
struct ID;
|
||||
struct ListBase;
|
||||
struct SpaceOutliner;
|
||||
|
||||
@@ -38,7 +39,8 @@ class AbstractTreeElement {
|
||||
|
||||
static std::unique_ptr<AbstractTreeElement> create_from_type(int type,
|
||||
TreeElement &legacy_te,
|
||||
void *idv);
|
||||
ID *owner_id,
|
||||
void *create_data);
|
||||
|
||||
/**
|
||||
* Check if the type is expandable in current context.
|
||||
@@ -100,12 +102,18 @@ class AbstractTreeElement {
|
||||
};
|
||||
|
||||
/**
|
||||
* TODO: this function needs to be split up! It's getting a bit too large...
|
||||
*
|
||||
* \note "ID" is not always a real ID.
|
||||
* \note If child items are only added to the tree if the item is open,
|
||||
* the `TSE_` type _must_ be added to #outliner_element_needs_rebuild_on_open_change().
|
||||
* \note If child items are only added to the tree if the item is open, the `TSE_` type _must_ be
|
||||
* added to #outliner_element_needs_rebuild_on_open_change().
|
||||
*
|
||||
* \param owner_id: The ID owning the represented data (or the ID itself if the element represents
|
||||
* an ID directly). This is crucial to recognize tree elements over rebuilds, so
|
||||
* that state like opened and selected is preserved. If this is not null, the \a
|
||||
* create_data pointer will be used instead, refer to its description.
|
||||
* \param create_data: Data passed to the constructor of the corresponding #AbstractTreeElement
|
||||
* sub-type. If \a owner_id is not set, this pointer will be stored in an
|
||||
* attempt to identify the element over rebuilds, so that state like opened and
|
||||
* selected is preserved. Of course that won't work for volatile data (like
|
||||
* stack variables).
|
||||
* \param expand: If true, the element may add its own sub-tree. E.g. objects will list their
|
||||
* animation data, object data, constraints, modifiers, ... This often adds visual
|
||||
* noise, and can be expensive to add in big scenes. So prefer setting this to
|
||||
@@ -113,7 +121,8 @@ class AbstractTreeElement {
|
||||
*/
|
||||
TreeElement *outliner_add_element(SpaceOutliner *space_outliner,
|
||||
ListBase *lb,
|
||||
void *idv,
|
||||
ID *owner_id,
|
||||
void *create_data,
|
||||
TreeElement *parent,
|
||||
short type,
|
||||
short index,
|
||||
|
||||
@@ -31,9 +31,18 @@ TreeElementAnimData::TreeElementAnimData(TreeElement &legacy_te, AnimData &anim_
|
||||
|
||||
void TreeElementAnimData::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
if (!anim_data_.action) {
|
||||
return;
|
||||
}
|
||||
|
||||
/* Animation data-block itself. */
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, anim_data_.action, &legacy_te_, TSE_SOME_ID, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(anim_data_.action),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
|
||||
expand_drivers(space_outliner);
|
||||
expand_NLA_tracks(space_outliner);
|
||||
@@ -45,7 +54,7 @@ void TreeElementAnimData::expand_drivers(SpaceOutliner &space_outliner) const
|
||||
return;
|
||||
}
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &anim_data_, &legacy_te_, TSE_DRIVER_BASE, 0);
|
||||
&space_outliner, &legacy_te_.subtree, nullptr, &anim_data_, &legacy_te_, TSE_DRIVER_BASE, 0);
|
||||
}
|
||||
|
||||
void TreeElementAnimData::expand_NLA_tracks(SpaceOutliner &space_outliner) const
|
||||
@@ -53,7 +62,8 @@ void TreeElementAnimData::expand_NLA_tracks(SpaceOutliner &space_outliner) const
|
||||
if (BLI_listbase_is_empty(&anim_data_.nla_tracks)) {
|
||||
return;
|
||||
}
|
||||
outliner_add_element(&space_outliner, &legacy_te_.subtree, &anim_data_, &legacy_te_, TSE_NLA, 0);
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, nullptr, &anim_data_, &legacy_te_, TSE_NLA, 0);
|
||||
}
|
||||
|
||||
} // namespace blender::ed::outliner
|
||||
|
||||
@@ -33,10 +33,13 @@ void TreeElementDeformGroupBase::expand(SpaceOutliner &space_outliner) const
|
||||
int index;
|
||||
LISTBASE_FOREACH_INDEX (bDeformGroup *, defgroup, defbase, index) {
|
||||
|
||||
DeformGroupElementCreateData defgroup_data = {&object_, defgroup};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &defgroup_data, &legacy_te_, TSE_DEFGROUP, index);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
defgroup,
|
||||
&legacy_te_,
|
||||
TSE_DEFGROUP,
|
||||
index);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -42,8 +42,13 @@ void TreeElementDriverBase::expand(SpaceOutliner &space_outliner) const
|
||||
DRIVER_TARGETS_USED_LOOPER_BEGIN (dvar) {
|
||||
if (lastadded != dtar->id) {
|
||||
/* XXX this lastadded check is rather lame, and also fails quite badly... */
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, dtar->id, &legacy_te_, TSE_LINKED_OB, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
dtar->id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
lastadded = dtar->id;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -31,11 +31,10 @@ void TreeElementGPencilEffectBase::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
int index;
|
||||
LISTBASE_FOREACH_INDEX (ShaderFxData *, fx, &object_.shader_fx, index) {
|
||||
GPencilEffectElementCreateData gp_effect_data = {&object_, fx};
|
||||
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&gp_effect_data,
|
||||
&object_.id,
|
||||
fx,
|
||||
&legacy_te_,
|
||||
TSE_GPENCIL_EFFECT,
|
||||
index);
|
||||
@@ -57,7 +56,8 @@ void TreeElementGPencilEffect::expand(SpaceOutliner &space_outliner) const
|
||||
if (fx_.type == eShaderFxType_Swirl) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((SwirlShaderFxData *)(&fx_))->object,
|
||||
reinterpret_cast<ID *>(((SwirlShaderFxData *)(&fx_))->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
|
||||
@@ -17,8 +17,9 @@
|
||||
namespace blender::ed::outliner {
|
||||
|
||||
TreeElementGreasePencilNode::TreeElementGreasePencilNode(TreeElement &legacy_te,
|
||||
GreasePencil &owner_grease_pencil,
|
||||
bke::greasepencil::TreeNode &node)
|
||||
: AbstractTreeElement(legacy_te), node_(node)
|
||||
: AbstractTreeElement(legacy_te), owner_grease_pencil_(owner_grease_pencil), node_(node)
|
||||
{
|
||||
BLI_assert(legacy_te.store_elem->type == TSE_GREASE_PENCIL_NODE);
|
||||
legacy_te.name = node.name().c_str();
|
||||
@@ -30,8 +31,13 @@ void TreeElementGreasePencilNode::expand(SpaceOutliner &space_outliner) const
|
||||
return;
|
||||
}
|
||||
LISTBASE_FOREACH_BACKWARD (GreasePencilLayerTreeNode *, child, &node_.as_group().children) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, child, &legacy_te_, TSE_GREASE_PENCIL_NODE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&owner_grease_pencil_.id,
|
||||
child,
|
||||
&legacy_te_,
|
||||
TSE_GREASE_PENCIL_NODE,
|
||||
0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -13,14 +13,18 @@
|
||||
namespace blender::bke::greasepencil {
|
||||
class TreeNode;
|
||||
} // namespace blender::bke::greasepencil
|
||||
struct GreasePencil;
|
||||
|
||||
namespace blender::ed::outliner {
|
||||
|
||||
class TreeElementGreasePencilNode final : public AbstractTreeElement {
|
||||
GreasePencil &owner_grease_pencil_;
|
||||
blender::bke::greasepencil::TreeNode &node_;
|
||||
|
||||
public:
|
||||
TreeElementGreasePencilNode(TreeElement &legacy_te, blender::bke::greasepencil::TreeNode &node);
|
||||
TreeElementGreasePencilNode(TreeElement &legacy_te,
|
||||
GreasePencil &owner_grease_pencil,
|
||||
blender::bke::greasepencil::TreeNode &node);
|
||||
|
||||
void expand(SpaceOutliner &) const override;
|
||||
|
||||
|
||||
@@ -129,18 +129,17 @@ bool TreeElementID::expand_poll(const SpaceOutliner &space_outliner) const
|
||||
void TreeElementID::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
/* Not all IDs support animation data. Will be null then. */
|
||||
const AnimData *anim_data = BKE_animdata_from_id(&id_);
|
||||
AnimData *anim_data = BKE_animdata_from_id(&id_);
|
||||
if (anim_data) {
|
||||
expand_animation_data(space_outliner, anim_data);
|
||||
}
|
||||
}
|
||||
|
||||
void TreeElementID::expand_animation_data(SpaceOutliner &space_outliner,
|
||||
const AnimData *anim_data) const
|
||||
void TreeElementID::expand_animation_data(SpaceOutliner &space_outliner, AnimData *anim_data) const
|
||||
{
|
||||
if (outliner_animdata_test(anim_data)) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &id_, &legacy_te_, TSE_ANIM_DATA, 0);
|
||||
&space_outliner, &legacy_te_.subtree, &id_, anim_data, &legacy_te_, TSE_ANIM_DATA, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -37,7 +37,7 @@ class TreeElementID : public AbstractTreeElement {
|
||||
|
||||
protected:
|
||||
/* ID types with animation data can use this. */
|
||||
void expand_animation_data(SpaceOutliner &, const AnimData *) const;
|
||||
void expand_animation_data(SpaceOutliner &, AnimData *) const;
|
||||
};
|
||||
|
||||
} // namespace blender::ed::outliner
|
||||
|
||||
@@ -52,9 +52,8 @@ void TreeElementIDArmature::expand_edit_bones(SpaceOutliner &space_outiner) cons
|
||||
{
|
||||
int a = 0;
|
||||
LISTBASE_FOREACH_INDEX (EditBone *, ebone, arm_.edbo, a) {
|
||||
EditBoneElementCreateData ebone_data = {&arm_.id, ebone};
|
||||
TreeElement *ten = outliner_add_element(
|
||||
&space_outiner, &legacy_te_.subtree, &ebone_data, &legacy_te_, TSE_EBONE, a);
|
||||
&space_outiner, &legacy_te_.subtree, &arm_.id, &ebone, &legacy_te_, TSE_EBONE, a);
|
||||
ebone->temp.p = ten;
|
||||
}
|
||||
/* make hierarchy */
|
||||
@@ -82,9 +81,7 @@ static void outliner_add_bone(SpaceOutliner *space_outliner,
|
||||
TreeElement *parent,
|
||||
int *a)
|
||||
{
|
||||
BoneElementCreateData bone_data = {id, curBone};
|
||||
|
||||
TreeElement *te = outliner_add_element(space_outliner, lb, &bone_data, parent, TSE_BONE, *a);
|
||||
TreeElement *te = outliner_add_element(space_outliner, lb, id, curBone, parent, TSE_BONE, *a);
|
||||
|
||||
(*a)++;
|
||||
|
||||
|
||||
@@ -31,8 +31,13 @@ void TreeElementIDCurve::expand(SpaceOutliner &space_outliner) const
|
||||
void TreeElementIDCurve::expand_materials(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
for (int a = 0; a < curve_.totcol; a++) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, curve_.mat[a], &legacy_te_, TSE_SOME_ID, a);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(curve_.mat[a]),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
a);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -36,7 +36,7 @@ void TreeElementIDGPLegacy::expand_layers(SpaceOutliner &space_outliner) const
|
||||
int index = 0;
|
||||
LISTBASE_FOREACH_BACKWARD (bGPDlayer *, gpl, &gpd_.layers) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, gpl, &legacy_te_, TSE_GP_LAYER, index);
|
||||
&space_outliner, &legacy_te_.subtree, &gpd_.id, gpl, &legacy_te_, TSE_GP_LAYER, index);
|
||||
index++;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,8 +34,13 @@ void TreeElementIDGreasePencil::expand_layer_tree(SpaceOutliner &space_outliner)
|
||||
LISTBASE_FOREACH_BACKWARD (
|
||||
GreasePencilLayerTreeNode *, child, &grease_pencil_.root_group().children)
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, child, &legacy_te_, TSE_GREASE_PENCIL_NODE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&grease_pencil_.id,
|
||||
child,
|
||||
&legacy_te_,
|
||||
TSE_GREASE_PENCIL_NODE,
|
||||
0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -37,7 +37,8 @@ void TreeElementIDLineStyle::expand_textures(SpaceOutliner &space_outliner) cons
|
||||
if (linestyle_.mtex[a]) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
(linestyle_.mtex[a])->tex,
|
||||
reinterpret_cast<ID *>((linestyle_.mtex[a])->tex),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
a);
|
||||
|
||||
@@ -31,15 +31,25 @@ void TreeElementIDMesh::expand(SpaceOutliner &space_outliner) const
|
||||
|
||||
void TreeElementIDMesh::expand_key(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, mesh_.key, &legacy_te_, TSE_SOME_ID, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(mesh_.key),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDMesh::expand_materials(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
for (int a = 0; a < mesh_.totcol; a++) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, mesh_.mat[a], &legacy_te_, TSE_SOME_ID, a);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(mesh_.mat[a]),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
a);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -31,8 +31,13 @@ void TreeElementIDMetaBall::expand(SpaceOutliner &space_outliner) const
|
||||
void TreeElementIDMetaBall::expand_materials(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
for (int a = 0; a < metaball_.totcol; a++) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, metaball_.mat[a], &legacy_te_, TSE_SOME_ID, a);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(metaball_.mat[a]),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
a);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -53,8 +53,13 @@ void TreeElementIDObject::expand(SpaceOutliner &space_outliner) const
|
||||
|
||||
void TreeElementIDObject::expand_data(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, object_.data, &legacy_te_, TSE_SOME_ID, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
static_cast<ID *>(object_.data),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDObject::expand_pose(SpaceOutliner &space_outliner) const
|
||||
@@ -63,20 +68,30 @@ void TreeElementIDObject::expand_pose(SpaceOutliner &space_outliner) const
|
||||
return;
|
||||
}
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_POSE_BASE, 0);
|
||||
&space_outliner, &legacy_te_.subtree, &object_.id, nullptr, &legacy_te_, TSE_POSE_BASE, 0);
|
||||
|
||||
/* Pose Groups */
|
||||
if (!BLI_listbase_is_empty(&object_.pose->agroups)) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_POSEGRP_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_POSEGRP_BASE,
|
||||
0);
|
||||
}
|
||||
}
|
||||
|
||||
void TreeElementIDObject::expand_materials(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
for (int a = 0; a < object_.totcol; a++) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, object_.mat[a], &legacy_te_, TSE_SOME_ID, a);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(object_.mat[a]),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
a);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -85,15 +100,18 @@ void TreeElementIDObject::expand_constraints(SpaceOutliner &space_outliner) cons
|
||||
if (BLI_listbase_is_empty(&object_.constraints)) {
|
||||
return;
|
||||
}
|
||||
TreeElement *tenla = outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_CONSTRAINT_BASE, 0);
|
||||
TreeElement *tenla = outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_CONSTRAINT_BASE,
|
||||
0);
|
||||
|
||||
int index;
|
||||
LISTBASE_FOREACH_INDEX (bConstraint *, con, &object_.constraints, index) {
|
||||
ConstraintElementCreateData con_data = {&object_, con};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &tenla->subtree, &con_data, tenla, TSE_CONSTRAINT, index);
|
||||
&space_outliner, &tenla->subtree, &object_.id, con, tenla, TSE_CONSTRAINT, index);
|
||||
/* possible add all other types links? */
|
||||
}
|
||||
}
|
||||
@@ -103,8 +121,13 @@ void TreeElementIDObject::expand_modifiers(SpaceOutliner &space_outliner) const
|
||||
if (BLI_listbase_is_empty(&object_.modifiers)) {
|
||||
return;
|
||||
}
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_MODIFIER_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_MODIFIER_BASE,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDObject::expand_gpencil_modifiers(SpaceOutliner &space_outliner) const
|
||||
@@ -112,8 +135,13 @@ void TreeElementIDObject::expand_gpencil_modifiers(SpaceOutliner &space_outliner
|
||||
if (BLI_listbase_is_empty(&object_.greasepencil_modifiers)) {
|
||||
return;
|
||||
}
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_MODIFIER_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_MODIFIER_BASE,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDObject::expand_gpencil_effects(SpaceOutliner &space_outliner) const
|
||||
@@ -121,8 +149,13 @@ void TreeElementIDObject::expand_gpencil_effects(SpaceOutliner &space_outliner)
|
||||
if (BLI_listbase_is_empty(&object_.shader_fx)) {
|
||||
return;
|
||||
}
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_GPENCIL_EFFECT_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_GPENCIL_EFFECT_BASE,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDObject::expand_vertex_groups(SpaceOutliner &space_outliner) const
|
||||
@@ -134,8 +167,13 @@ void TreeElementIDObject::expand_vertex_groups(SpaceOutliner &space_outliner) co
|
||||
if (BLI_listbase_is_empty(defbase)) {
|
||||
return;
|
||||
}
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &object_, &legacy_te_, TSE_DEFGROUP_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_DEFGROUP_BASE,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDObject::expand_duplicated_group(SpaceOutliner &space_outliner) const
|
||||
@@ -143,7 +181,8 @@ void TreeElementIDObject::expand_duplicated_group(SpaceOutliner &space_outliner)
|
||||
if (object_.instance_collection && (object_.transflag & OB_DUPLICOLLECTION)) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
object_.instance_collection,
|
||||
reinterpret_cast<ID *>(object_.instance_collection),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
|
||||
@@ -34,25 +34,40 @@ void TreeElementIDScene::expand(SpaceOutliner &space_outliner) const
|
||||
void TreeElementIDScene::expand_view_layers(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &scene_, &legacy_te_, TSE_R_LAYER_BASE, 0);
|
||||
&space_outliner, &legacy_te_.subtree, &scene_.id, nullptr, &legacy_te_, TSE_R_LAYER_BASE, 0);
|
||||
}
|
||||
|
||||
void TreeElementIDScene::expand_world(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, scene_.world, &legacy_te_, TSE_SOME_ID, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(scene_.world),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDScene::expand_collections(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &scene_, &legacy_te_, TSE_SCENE_COLLECTION_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&scene_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SCENE_COLLECTION_BASE,
|
||||
0);
|
||||
}
|
||||
|
||||
void TreeElementIDScene::expand_objects(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &scene_, &legacy_te_, TSE_SCENE_OBJECTS_BASE, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&scene_.id,
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SCENE_OBJECTS_BASE,
|
||||
0);
|
||||
}
|
||||
|
||||
} // namespace blender::ed::outliner
|
||||
|
||||
@@ -30,8 +30,13 @@ void TreeElementIDTexture::expand(SpaceOutliner &space_outliner) const
|
||||
|
||||
void TreeElementIDTexture::expand_image(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, texture_.ima, &legacy_te_, TSE_SOME_ID, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(texture_.ima),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
}
|
||||
|
||||
} // namespace blender::ed::outliner
|
||||
|
||||
@@ -33,18 +33,24 @@ void TreeElementModifierBase::expand(SpaceOutliner &space_outliner) const
|
||||
LISTBASE_FOREACH_INDEX (ModifierData *, md, &object_.modifiers, index) {
|
||||
ModifierDataStoreElem md_store(md);
|
||||
|
||||
ModifierCreateElementData md_data = {&object_, &md_store};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &md_data, &legacy_te_, TSE_MODIFIER, index);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
&md_store,
|
||||
&legacy_te_,
|
||||
TSE_MODIFIER,
|
||||
index);
|
||||
}
|
||||
LISTBASE_FOREACH_INDEX (GpencilModifierData *, md, &object_.greasepencil_modifiers, index) {
|
||||
ModifierDataStoreElem md_store(md);
|
||||
|
||||
ModifierCreateElementData md_data = {&object_, &md_store};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &md_data, &legacy_te_, TSE_MODIFIER, index);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
&md_store,
|
||||
&legacy_te_,
|
||||
TSE_MODIFIER,
|
||||
index);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -70,7 +76,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
if (md->type == eModifierType_Lattice) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((LatticeModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((LatticeModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
@@ -78,7 +85,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
else if (md->type == eModifierType_Curve) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((CurveModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((CurveModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
@@ -86,7 +94,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
else if (md->type == eModifierType_Armature) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((ArmatureModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((ArmatureModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
@@ -94,7 +103,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
else if (md->type == eModifierType_Hook) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((HookModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((HookModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
@@ -102,10 +112,13 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
else if (md->type == eModifierType_ParticleSystem) {
|
||||
ParticleSystem *psys = ((ParticleSystemModifierData *)md)->psys;
|
||||
|
||||
ParticleSystemElementCreateData psys_data = {&object_, psys};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &psys_data, &legacy_te_, TSE_LINKED_PSYS, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
psys,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_PSYS,
|
||||
0);
|
||||
}
|
||||
}
|
||||
if (md_.type == GPENCIL_MODIFIER_TYPE) {
|
||||
@@ -113,7 +126,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
if (md->type == eGpencilModifierType_Armature) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((ArmatureGpencilModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((ArmatureGpencilModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
@@ -121,7 +135,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
else if (md->type == eGpencilModifierType_Hook) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((HookGpencilModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((HookGpencilModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
@@ -129,7 +144,8 @@ void TreeElementModifier::expand(SpaceOutliner &space_outliner) const
|
||||
else if (md->type == eGpencilModifierType_Lattice) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
((LatticeGpencilModifierData *)md)->object,
|
||||
reinterpret_cast<ID *>(((LatticeGpencilModifierData *)md)->object),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_LINKED_OB,
|
||||
0);
|
||||
|
||||
@@ -32,7 +32,8 @@ void TreeElementNLA::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
int a = 0;
|
||||
for (NlaTrack *nlt : ListBaseWrapper<NlaTrack>(anim_data_.nla_tracks)) {
|
||||
outliner_add_element(&space_outliner, &legacy_te_.subtree, nlt, &legacy_te_, TSE_NLA_TRACK, a);
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, nullptr, nlt, &legacy_te_, TSE_NLA_TRACK, a);
|
||||
a++;
|
||||
}
|
||||
}
|
||||
@@ -50,8 +51,13 @@ void TreeElementNLATrack::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
int a = 0;
|
||||
for (NlaStrip *strip : ListBaseWrapper<NlaStrip>(track_.strips)) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, strip->act, &legacy_te_, TSE_NLA_ACTION, a);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(strip->act),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_NLA_ACTION,
|
||||
a);
|
||||
a++;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -378,6 +378,7 @@ void OverrideRNAPathTreeBuilder::build_path(TreeElement &parent,
|
||||
else if (!path_te_map.contains(override_data.override_property.rna_path)) {
|
||||
outliner_add_element(&space_outliner_,
|
||||
&te_to_expand->subtree,
|
||||
&override_data.id,
|
||||
&override_data,
|
||||
te_to_expand,
|
||||
TSE_LIBRARY_OVERRIDE,
|
||||
@@ -434,6 +435,7 @@ void OverrideRNAPathTreeBuilder::ensure_entire_collection(
|
||||
|
||||
current_te = outliner_add_element(&space_outliner_,
|
||||
&te_to_expand.subtree,
|
||||
&override_op_data.id,
|
||||
/* Element will store a copy. */
|
||||
&override_op_data,
|
||||
&te_to_expand,
|
||||
@@ -477,6 +479,7 @@ TreeElement &OverrideRNAPathTreeBuilder::ensure_label_element_for_prop(
|
||||
return *path_te_map.lookup_or_add_cb(elem_path, [&]() {
|
||||
TreeElement *new_te = outliner_add_element(&space_outliner_,
|
||||
&parent.subtree,
|
||||
nullptr,
|
||||
(void *)RNA_property_ui_name(&prop),
|
||||
&parent,
|
||||
TSE_GENERIC_LABEL,
|
||||
@@ -500,6 +503,7 @@ TreeElement &OverrideRNAPathTreeBuilder::ensure_label_element_for_ptr(TreeElemen
|
||||
TreeElement *new_te = outliner_add_element(
|
||||
&space_outliner_,
|
||||
&parent.subtree,
|
||||
nullptr,
|
||||
(void *)(dyn_name ? dyn_name : RNA_struct_ui_name(ptr.type)),
|
||||
&parent,
|
||||
TSE_GENERIC_LABEL,
|
||||
|
||||
@@ -37,23 +37,29 @@ void TreeElementPoseBase::expand(SpaceOutliner &space_outliner) const
|
||||
int const_index = 1000; /* ensure unique id for bone constraints */
|
||||
int a;
|
||||
LISTBASE_FOREACH_INDEX (bPoseChannel *, pchan, &object_.pose->chanbase, a) {
|
||||
PoseChannelElementCreateData pchan_data = {&object_, pchan};
|
||||
|
||||
TreeElement *ten = outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &pchan_data, &legacy_te_, TSE_POSE_CHANNEL, a);
|
||||
TreeElement *ten = outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
&object_.id,
|
||||
pchan,
|
||||
&legacy_te_,
|
||||
TSE_POSE_CHANNEL,
|
||||
a);
|
||||
pchan->temp = (void *)ten;
|
||||
|
||||
if (!BLI_listbase_is_empty(&pchan->constraints)) {
|
||||
/* Object *target; */
|
||||
TreeElement *tenla1 = outliner_add_element(
|
||||
&space_outliner, &ten->subtree, &object_, ten, TSE_CONSTRAINT_BASE, 0);
|
||||
&space_outliner, &ten->subtree, &object_.id, nullptr, ten, TSE_CONSTRAINT_BASE, 0);
|
||||
/* char *str; */
|
||||
|
||||
LISTBASE_FOREACH (bConstraint *, con, &pchan->constraints) {
|
||||
ConstraintElementCreateData con_data = {&object_, con};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &tenla1->subtree, &con_data, tenla1, TSE_CONSTRAINT, const_index);
|
||||
outliner_add_element(&space_outliner,
|
||||
&tenla1->subtree,
|
||||
&object_.id,
|
||||
con,
|
||||
tenla1,
|
||||
TSE_CONSTRAINT,
|
||||
const_index);
|
||||
/* possible add all other types links? */
|
||||
}
|
||||
const_index++;
|
||||
|
||||
@@ -31,10 +31,8 @@ void TreeElementPoseGroupBase::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
int index;
|
||||
LISTBASE_FOREACH_INDEX (bActionGroup *, agrp, &object_.pose->agroups, index) {
|
||||
PoseGroupElementCreateData posegrp_data = {&object_, agrp};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &posegrp_data, &legacy_te_, TSE_POSEGRP, index);
|
||||
&space_outliner, &legacy_te_.subtree, &object_.id, agrp, &legacy_te_, TSE_POSEGRP, index);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -115,8 +115,13 @@ void TreeElementRNAStruct::expand(SpaceOutliner &space_outliner) const
|
||||
PointerRNA propptr;
|
||||
RNA_property_collection_lookup_int(&ptr, iterprop, index, &propptr);
|
||||
if (!(RNA_property_flag(static_cast<PropertyRNA *>(propptr.data)) & PROP_HIDDEN)) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &ptr, &legacy_te_, TSE_RNA_PROPERTY, index);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
ptr.owner_id,
|
||||
&ptr,
|
||||
&legacy_te_,
|
||||
TSE_RNA_PROPERTY,
|
||||
index);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -165,8 +170,13 @@ void TreeElementRNAProperty::expand(SpaceOutliner &space_outliner) const
|
||||
|
||||
if (pptr.data) {
|
||||
if (TSELEM_OPEN(&tselem, &space_outliner)) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &pptr, &legacy_te_, TSE_RNA_STRUCT, -1);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
pptr.owner_id,
|
||||
&pptr,
|
||||
&legacy_te_,
|
||||
TSE_RNA_STRUCT,
|
||||
-1);
|
||||
}
|
||||
else {
|
||||
legacy_te_.flag |= TE_PRETEND_HAS_CHILDREN;
|
||||
@@ -181,8 +191,13 @@ void TreeElementRNAProperty::expand(SpaceOutliner &space_outliner) const
|
||||
for (int index = 0; index < tot; index++) {
|
||||
PointerRNA pptr;
|
||||
RNA_property_collection_lookup_int(&rna_ptr, rna_prop_, index, &pptr);
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &pptr, &legacy_te_, TSE_RNA_STRUCT, index);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
pptr.owner_id,
|
||||
&pptr,
|
||||
&legacy_te_,
|
||||
TSE_RNA_STRUCT,
|
||||
index);
|
||||
}
|
||||
}
|
||||
else if (tot) {
|
||||
@@ -197,6 +212,7 @@ void TreeElementRNAProperty::expand(SpaceOutliner &space_outliner) const
|
||||
for (int index = 0; index < tot; index++) {
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
rna_ptr.owner_id,
|
||||
&rna_ptr,
|
||||
&legacy_te_,
|
||||
TSE_RNA_ARRAY_ELEM,
|
||||
|
||||
@@ -31,7 +31,13 @@ TreeElementSceneObjectsBase::TreeElementSceneObjectsBase(TreeElement &legacy_te,
|
||||
void TreeElementSceneObjectsBase::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
FOREACH_SCENE_OBJECT_BEGIN (&scene_, ob) {
|
||||
outliner_add_element(&space_outliner, &legacy_te_.subtree, ob, &legacy_te_, TSE_SOME_ID, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
reinterpret_cast<ID *>(ob),
|
||||
nullptr,
|
||||
&legacy_te_,
|
||||
TSE_SOME_ID,
|
||||
0);
|
||||
}
|
||||
FOREACH_SCENE_OBJECT_END;
|
||||
outliner_make_object_parent_hierarchy(&legacy_te_.subtree);
|
||||
|
||||
@@ -41,12 +41,17 @@ void TreeElementSequence::expand(SpaceOutliner &space_outliner) const
|
||||
if (sequence_.type == SEQ_TYPE_META) {
|
||||
LISTBASE_FOREACH (Sequence *, child, &sequence_.seqbase) {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, child, &legacy_te_, TSE_SEQUENCE, 0);
|
||||
&space_outliner, &legacy_te_.subtree, nullptr, child, &legacy_te_, TSE_SEQUENCE, 0);
|
||||
}
|
||||
}
|
||||
else {
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, sequence_.strip, &legacy_te_, TSE_SEQ_STRIP, 0);
|
||||
outliner_add_element(&space_outliner,
|
||||
&legacy_te_.subtree,
|
||||
nullptr,
|
||||
sequence_.strip,
|
||||
&legacy_te_,
|
||||
TSE_SEQ_STRIP,
|
||||
0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -30,10 +30,8 @@ TreeElementViewLayerBase::TreeElementViewLayerBase(TreeElement &legacy_te, Scene
|
||||
void TreeElementViewLayerBase::expand(SpaceOutliner &space_outliner) const
|
||||
{
|
||||
for (auto *view_layer : ListBaseWrapper<ViewLayer>(scene_.view_layers)) {
|
||||
ViewLayerElementCreateData view_layer_data = {&scene_, view_layer};
|
||||
|
||||
outliner_add_element(
|
||||
&space_outliner, &legacy_te_.subtree, &view_layer_data, &legacy_te_, TSE_R_LAYER, 0);
|
||||
&space_outliner, &legacy_te_.subtree, &scene_.id, view_layer, &legacy_te_, TSE_R_LAYER, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user