Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'intern/cycles/bvh/node.h')
-rw-r--r--intern/cycles/bvh/node.h255
1 files changed, 255 insertions, 0 deletions
diff --git a/intern/cycles/bvh/node.h b/intern/cycles/bvh/node.h
new file mode 100644
index 00000000000..d5de9e062fc
--- /dev/null
+++ b/intern/cycles/bvh/node.h
@@ -0,0 +1,255 @@
+/*
+ * Adapted from code copyright 2009-2010 NVIDIA Corporation
+ * Modifications Copyright 2011, Blender Foundation.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __BVH_NODE_H__
+#define __BVH_NODE_H__
+
+#include "util/boundbox.h"
+#include "util/types.h"
+
+CCL_NAMESPACE_BEGIN
+
+enum BVH_STAT {
+ BVH_STAT_NODE_COUNT,
+ BVH_STAT_INNER_COUNT,
+ BVH_STAT_LEAF_COUNT,
+ BVH_STAT_TRIANGLE_COUNT,
+ BVH_STAT_CHILDNODE_COUNT,
+ BVH_STAT_ALIGNED_COUNT,
+ BVH_STAT_UNALIGNED_COUNT,
+ BVH_STAT_ALIGNED_INNER_COUNT,
+ BVH_STAT_UNALIGNED_INNER_COUNT,
+ BVH_STAT_ALIGNED_LEAF_COUNT,
+ BVH_STAT_UNALIGNED_LEAF_COUNT,
+ BVH_STAT_DEPTH,
+};
+
+class BVHParams;
+
+class BVHNode {
+ public:
+ virtual ~BVHNode()
+ {
+ delete aligned_space;
+ }
+
+ virtual bool is_leaf() const = 0;
+ virtual int num_children() const = 0;
+ virtual BVHNode *get_child(int i) const = 0;
+ virtual int num_triangles() const
+ {
+ return 0;
+ }
+ virtual void print(int depth = 0) const = 0;
+
+ inline void set_aligned_space(const Transform &aligned_space)
+ {
+ is_unaligned = true;
+ if (this->aligned_space == NULL) {
+ this->aligned_space = new Transform(aligned_space);
+ }
+ else {
+ *this->aligned_space = aligned_space;
+ }
+ }
+
+ inline Transform get_aligned_space() const
+ {
+ if (aligned_space == NULL) {
+ return transform_identity();
+ }
+ return *aligned_space;
+ }
+
+ inline bool has_unaligned() const
+ {
+ if (is_leaf()) {
+ return false;
+ }
+ for (int i = 0; i < num_children(); ++i) {
+ if (get_child(i)->is_unaligned) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ // Subtree functions
+ int getSubtreeSize(BVH_STAT stat = BVH_STAT_NODE_COUNT) const;
+ float computeSubtreeSAHCost(const BVHParams &p, float probability = 1.0f) const;
+ void deleteSubtree();
+
+ uint update_visibility();
+ void update_time();
+
+ /* Dump the content of the tree as a graphviz file. */
+ void dump_graph(const char *filename);
+
+ // Properties.
+ BoundBox bounds;
+ uint visibility;
+
+ bool is_unaligned;
+
+ /* TODO(sergey): Can be stored as 3x3 matrix, but better to have some
+ * utilities and type defines in util_transform first.
+ */
+ Transform *aligned_space;
+
+ float time_from, time_to;
+
+ protected:
+ explicit BVHNode(const BoundBox &bounds)
+ : bounds(bounds),
+ visibility(0),
+ is_unaligned(false),
+ aligned_space(NULL),
+ time_from(0.0f),
+ time_to(1.0f)
+ {
+ }
+
+ explicit BVHNode(const BVHNode &other)
+ : bounds(other.bounds),
+ visibility(other.visibility),
+ is_unaligned(other.is_unaligned),
+ aligned_space(NULL),
+ time_from(other.time_from),
+ time_to(other.time_to)
+ {
+ if (other.aligned_space != NULL) {
+ assert(other.is_unaligned);
+ aligned_space = new Transform();
+ *aligned_space = *other.aligned_space;
+ }
+ else {
+ assert(!other.is_unaligned);
+ }
+ }
+};
+
+class InnerNode : public BVHNode {
+ public:
+ static constexpr int kNumMaxChildren = 8;
+
+ InnerNode(const BoundBox &bounds, BVHNode *child0, BVHNode *child1)
+ : BVHNode(bounds), num_children_(2)
+ {
+ children[0] = child0;
+ children[1] = child1;
+ reset_unused_children();
+
+ if (child0 && child1) {
+ visibility = child0->visibility | child1->visibility;
+ }
+ else {
+ /* Happens on build cancel. */
+ visibility = 0;
+ }
+ }
+
+ InnerNode(const BoundBox &bounds, BVHNode **children, const int num_children)
+ : BVHNode(bounds), num_children_(num_children)
+ {
+ visibility = 0;
+ time_from = FLT_MAX;
+ time_to = -FLT_MAX;
+ for (int i = 0; i < num_children; ++i) {
+ assert(children[i] != NULL);
+ visibility |= children[i]->visibility;
+ this->children[i] = children[i];
+ time_from = min(time_from, children[i]->time_from);
+ time_to = max(time_to, children[i]->time_to);
+ }
+ reset_unused_children();
+ }
+
+ /* NOTE: This function is only used during binary BVH builder, and it
+ * supposed to be configured to have 2 children which will be filled-in in a
+ * bit. But this is important to have children reset to NULL. */
+ explicit InnerNode(const BoundBox &bounds) : BVHNode(bounds), num_children_(0)
+ {
+ reset_unused_children();
+ visibility = 0;
+ num_children_ = 2;
+ }
+
+ bool is_leaf() const
+ {
+ return false;
+ }
+ int num_children() const
+ {
+ return num_children_;
+ }
+ BVHNode *get_child(int i) const
+ {
+ assert(i >= 0 && i < num_children_);
+ return children[i];
+ }
+ void print(int depth) const;
+
+ int num_children_;
+ BVHNode *children[kNumMaxChildren];
+
+ protected:
+ void reset_unused_children()
+ {
+ for (int i = num_children_; i < kNumMaxChildren; ++i) {
+ children[i] = NULL;
+ }
+ }
+};
+
+class LeafNode : public BVHNode {
+ public:
+ LeafNode(const BoundBox &bounds, uint visibility, int lo, int hi)
+ : BVHNode(bounds), lo(lo), hi(hi)
+ {
+ this->bounds = bounds;
+ this->visibility = visibility;
+ }
+
+ LeafNode(const LeafNode &other) : BVHNode(other), lo(other.lo), hi(other.hi)
+ {
+ }
+
+ bool is_leaf() const
+ {
+ return true;
+ }
+ int num_children() const
+ {
+ return 0;
+ }
+ BVHNode *get_child(int) const
+ {
+ return NULL;
+ }
+ int num_triangles() const
+ {
+ return hi - lo;
+ }
+ void print(int depth) const;
+
+ int lo;
+ int hi;
+};
+
+CCL_NAMESPACE_END
+
+#endif /* __BVH_NODE_H__ */