debug gui select/hide nodes
[laserbrain_demo] / src / snode.cc
index bce8c0a..b171f35 100644 (file)
@@ -11,7 +11,8 @@ SceneNode::SceneNode()
        scene = 0;
        parent = 0;
        name = 0;
-       bvol_valid = false;
+       visible = true;
+       local_bvol_valid = false;
 }
 
 SceneNode::SceneNode(Object *obj)
@@ -20,7 +21,8 @@ SceneNode::SceneNode(Object *obj)
        scene = 0;
        parent = 0;
        name = 0;
-       bvol_valid = false;
+       visible = true;
+       local_bvol_valid = false;
        add_object(obj);
 }
 
@@ -55,8 +57,6 @@ void SceneNode::add_child(SceneNode *node)
        children.push_back(node);
        node->parent = this;
        node->scene = scene;
-
-       bvol_valid = false;
 }
 
 bool SceneNode::remove_child(SceneNode *node)
@@ -69,8 +69,6 @@ bool SceneNode::remove_child(SceneNode *node)
                node->parent = 0;
                node->scene = 0;
                children.erase(it);
-
-               bvol_valid = false;
                return true;
        }
        return false;
@@ -102,7 +100,7 @@ void SceneNode::add_object(Object *obj)
        this->obj.push_back(obj);
        obj->node = this;
 
-       bvol_valid = false;
+       local_bvol_valid = false;
 }
 
 bool SceneNode::remove_object(Object *o)
@@ -118,7 +116,7 @@ bool SceneNode::remove_object(Object *o)
        }
        obj.erase(it);
 
-       bvol_valid = false;
+       local_bvol_valid = false;
        return true;
 }
 
@@ -209,8 +207,21 @@ void SceneNode::update(float dt)
 
        if(debug_gui) {
                if(parent_expanded) {
-                       int flags = children.empty() ? ImGuiTreeNodeFlags_Leaf : 0;
+                       ImGui::PushID(this);
+                       ImGui::AlignTextToFramePadding();
+
+                       int flags = ImGuiTreeNodeFlags_OpenOnArrow | ImGuiTreeNodeFlags_OpenOnDoubleClick;
+                       if(children.empty()) flags |= ImGuiTreeNodeFlags_Leaf;
+                       if(dbg_sel_node == this) flags |= ImGuiTreeNodeFlags_Selected;
                        expanded = ImGui::TreeNodeEx(name ? name : "<nameless node>", flags);
+                       if(ImGui::IsItemClicked()) {
+                               dbg_sel_node = this;
+                       }
+
+                       ImGui::NextColumn();
+                       ImGui::Checkbox("##vis", &visible);
+                       ImGui::NextColumn();
+                       ImGui::PopID();
                }
        }
 
@@ -287,15 +298,54 @@ bool SceneNode::intersect(const Ray &ray, HitPoint *hit) const
        return false;
 }
 
-const Box &SceneNode::calc_bounds()
+const AABox &SceneNode::calc_local_bounds()
 {
-       // TODO
+       local_bvol = AABox(Vec3(FLT_MAX, FLT_MAX, FLT_MAX), Vec3(-FLT_MAX, -FLT_MAX, -FLT_MAX));
+
+       // calculate the axis-aligned bounding box of all objects in this node
+       int nobj = obj.size();
+       for(int i=0; i<nobj; i++) {
+               AABox tmp = obj[i]->get_aabox();
+               calc_bounding_aabox(&local_bvol, &local_bvol, &tmp);
+       }
+
+       local_bvol_valid = true;
+       return local_bvol;
 }
 
-const Box &SceneNode::get_bounds() const
+const AABox &SceneNode::get_local_bounds() const
 {
-       if(!bvol_valid) {
-               return ((SceneNode*)this)->calc_bounds();
+       if(!local_bvol_valid) {
+               ((SceneNode*)this)->calc_local_bounds();
        }
-       return bvol;
+       return local_bvol;
+}
+
+AABox SceneNode::get_node_bounds() const
+{
+       get_local_bounds();     // validate local_bvol
+
+       // calculate the transformed local_bvol
+       Box node_bbox = Box(local_bvol, xform);
+
+       // then calculate the axis-aligned bounding box
+       AABox aabox;
+       calc_bounding_aabox(&aabox, &node_bbox);
+       return aabox;
+}
+
+AABox SceneNode::get_bounds() const
+{
+       AABox sub_aabb = AABox(Vec3(FLT_MAX, FLT_MAX, FLT_MAX), Vec3(-FLT_MAX, -FLT_MAX, -FLT_MAX));
+
+       // calculate the bounding box of all children
+       int nchild = children.size();
+       for(int i=0; i<nchild; i++) {
+               AABox tmp = children[i]->get_bounds();
+               calc_bounding_aabox(&sub_aabb, &sub_aabb, &tmp);
+       }
+
+       AABox aabb = get_node_bounds();
+       calc_bounding_aabox(&aabb, &aabb, &sub_aabb);
+       return aabb;
 }