/* Begin kd-tree setup, go through full range starting with x axis. */ void VertexBufferRoot::setupTree( VertexData& data ) { // data is VertexData, _data is VertexBufferData _data.clear(); const Axis axis = data.getLongestAxis( 0, data.triangles.size() ); VertexBufferNode::setupTree( data, 0, data.triangles.size(), axis, 0, _data ); VertexBufferNode::updateBoundingSphere(); VertexBufferNode::updateRange(); #if 0 // re-test all points to be in the bounding sphere Vertex center( _boundingSphere.array ); float radius = _boundingSphere.w(); float radiusSquared = radius * radius; for( size_t offset = 0; offset < _data.vertices.size(); ++offset ) { const Vertex& vertex = _data.vertices[ offset ]; const Vertex centerToPoint = vertex - center; const float distanceSquared = centerToPoint.squared_length(); EQASSERTINFO( distanceSquared <= radiusSquared, distanceSquared << " > " << radiusSquared ); } #endif }
/* Continue kd-tree setup, create intermediary or leaf nodes as required. */ void VertexBufferNode::setupTree( VertexData& data, const Index start, const Index length, const Axis axis, const size_t depth, VertexBufferData& globalData, boost::progress_display& progress ) { data.sort( start, length, axis ); const Index median = start + ( length / 2 ); // left child will include elements smaller than the median const Index leftLength = length / 2; const bool subdivideLeft = _subdivide( leftLength, depth ); if( subdivideLeft ) _left = new VertexBufferNode; else _left = new VertexBufferLeaf( globalData ); // right child will include elements equal to or greater than the median const Index rightLength = ( length + 1 ) / 2; const bool subdivideRight = _subdivide( rightLength, depth ); if( subdivideRight ) _right = new VertexBufferNode; else _right = new VertexBufferLeaf( globalData ); // move to next axis and continue contruction in the child nodes const Axis newAxisLeft = subdivideLeft ? data.getLongestAxis( start , leftLength ) : AXIS_X; const Axis newAxisRight = subdivideRight ? data.getLongestAxis( median, rightLength ) : AXIS_X; static_cast< VertexBufferNode* > ( _left )->setupTree( data, start, leftLength, newAxisLeft, depth+1, globalData, progress ); static_cast< VertexBufferNode* > ( _right )->setupTree( data, median, rightLength, newAxisRight, depth+1, globalData, progress ); if( depth == 3 ) ++progress; }
/* Begin kd-tree setup, go through full range starting with x axis. */ void VertexBufferRoot::setupTree( VertexData& data, boost::progress_display& progress ) { // data is VertexData, _data is VertexBufferData _data.clear(); const Axis axis = data.getLongestAxis( 0, data.triangles.size() ); VertexBufferNode::setupTree( data, 0, data.triangles.size(), axis, 0, _data, progress ); VertexBufferNode::updateBoundingSphere(); VertexBufferNode::updateRange(); }