diff options
author | Dalai Felinto <dfelinto@gmail.com> | 2018-01-16 01:08:50 +0300 |
---|---|---|
committer | Dalai Felinto <dfelinto@gmail.com> | 2018-01-16 01:19:12 +0300 |
commit | 1e9bc60777421b861852f9289d1ca71a69bedc3f (patch) | |
tree | b38dc414a3b6af3a118305ef360c5f043bfc5da9 | |
parent | 59fcfaf5c3574d7de97b0333e1b08609e96a3d86 (diff) |
Fix collection visibility evaluation
Collection A [disabled]
-> Collection B
-> Collection C
-> object
Object should be invisible, but it is not. Reported by Antonio Vazquez.
Bug introduced on: 1f5106de610b
-rw-r--r-- | source/blender/blenkernel/intern/layer.c | 31 | ||||
-rw-r--r-- | tests/python/view_layer/CMakeLists.txt | 1 | ||||
-rw-r--r-- | tests/python/view_layer/test_evaluation_visibility_j.py | 61 |
3 files changed, 83 insertions, 10 deletions
diff --git a/source/blender/blenkernel/intern/layer.c b/source/blender/blenkernel/intern/layer.c index 288dcb34439..c63cefbcd8c 100644 --- a/source/blender/blenkernel/intern/layer.c +++ b/source/blender/blenkernel/intern/layer.c @@ -2099,18 +2099,22 @@ static const char *collection_type_lookup[] = "Group Internal", /* COLLECTION_TYPE_GROUP_INTERNAL */ }; +/** + * \note We can't use layer_collection->flag because of 3 level nesting (where parent is visible, but not grand-parent) + * So layer_collection->flag_evaluated is expected to be up to date with layer_collection->flag. + */ static bool layer_collection_visible_get(const EvaluationContext *eval_ctx, LayerCollection *layer_collection) { - bool is_visible = (layer_collection->flag & COLLECTION_DISABLED) == 0; + if (layer_collection->flag_evaluated & COLLECTION_DISABLED) { + return false; + } if (eval_ctx->mode == DAG_EVAL_VIEWPORT) { - is_visible &= (layer_collection->flag & COLLECTION_VIEWPORT) != 0; + return (layer_collection->flag_evaluated & COLLECTION_VIEWPORT) != 0; } else { - is_visible &= (layer_collection->flag & COLLECTION_RENDER) != 0; + return (layer_collection->flag_evaluated & COLLECTION_RENDER) != 0; } - - return is_visible; } void BKE_layer_eval_layer_collection(const EvaluationContext *eval_ctx, @@ -2129,15 +2133,22 @@ void BKE_layer_eval_layer_collection(const EvaluationContext *eval_ctx, /* visibility */ layer_collection->flag_evaluated = layer_collection->flag; - bool is_visible = layer_collection_visible_get(eval_ctx, layer_collection); - bool is_selectable = is_visible && ((layer_collection->flag & COLLECTION_SELECTABLE) != 0); if (parent_layer_collection != NULL) { - is_visible &= layer_collection_visible_get(eval_ctx, parent_layer_collection); - is_selectable &= (parent_layer_collection->flag_evaluated & COLLECTION_SELECTABLE) != 0; - layer_collection->flag_evaluated &= parent_layer_collection->flag_evaluated; + if (layer_collection_visible_get(eval_ctx, parent_layer_collection) == false) { + layer_collection->flag_evaluated |= COLLECTION_DISABLED; + } + + if ((parent_layer_collection->flag_evaluated & COLLECTION_DISABLED) || + (parent_layer_collection->flag_evaluated & COLLECTION_SELECTABLE) == 0) + { + layer_collection->flag_evaluated &= ~COLLECTION_SELECTABLE; + } } + const bool is_visible = layer_collection_visible_get(eval_ctx, layer_collection); + const bool is_selectable = is_visible && ((layer_collection->flag_evaluated & COLLECTION_SELECTABLE) != 0); + /* overrides */ if (is_visible) { if (parent_layer_collection == NULL) { diff --git a/tests/python/view_layer/CMakeLists.txt b/tests/python/view_layer/CMakeLists.txt index 3f7149a67ad..69b02416487 100644 --- a/tests/python/view_layer/CMakeLists.txt +++ b/tests/python/view_layer/CMakeLists.txt @@ -81,6 +81,7 @@ VIEW_LAYER_TEST(evaluation_visibility_f) VIEW_LAYER_TEST(evaluation_visibility_g) VIEW_LAYER_TEST(evaluation_visibility_h) VIEW_LAYER_TEST(evaluation_visibility_i) +VIEW_LAYER_TEST(evaluation_visibility_j) VIEW_LAYER_TEST(evaluation_selectability_a) VIEW_LAYER_TEST(evaluation_selectability_b) VIEW_LAYER_TEST(evaluation_selectability_c) diff --git a/tests/python/view_layer/test_evaluation_visibility_j.py b/tests/python/view_layer/test_evaluation_visibility_j.py new file mode 100644 index 00000000000..53810fe5599 --- /dev/null +++ b/tests/python/view_layer/test_evaluation_visibility_j.py @@ -0,0 +1,61 @@ +# ############################################################ +# Importing - Same For All Render Layer Tests +# ############################################################ + +import unittest +import os +import sys + +from view_layer_common import * + + +# ############################################################ +# Testing +# ############################################################ + +class UnitTesting(ViewLayerTesting): + def test_visibility_nested(self): + """ + See if the depsgraph evaluation is correct + """ + import bpy + + # delete all initial objects + while bpy.data.objects: + bpy.data.objects.remove(bpy.data.objects[0]) + + # delete all initial collections + scene = bpy.context.scene + master_collection = scene.master_collection + while master_collection.collections: + master_collection.collections.remove(master_collection.collections[0]) + + collection_parent = master_collection.collections.new('parent') + collection_nested = collection_parent.collections.new('child linked') + ob = bpy.data.objects.new('An Empty', None) + collection_nested.objects.link(ob) + + layer_collection = bpy.context.view_layer.collections.link(master_collection) + self.assertTrue(layer_collection.enabled) + + # Update depsgraph. + scene.update() + + self.assertTrue(ob.visible_get()) + + layer_collection.enabled = False + self.assertFalse(layer_collection.enabled) + + # Update depsgraph. + scene.update() + + self.assertFalse(ob.visible_get()) + + +# ############################################################ +# Main - Same For All Render Layer Tests +# ############################################################ + +if __name__ == '__main__': + UnitTesting._extra_arguments = setup_extra_arguments(__file__) + unittest.main() |