void Terrain::RenewNodes(const vec3& viewpoint, const QuadTree<TerrainNode>::Iterator& node) { //Check if this node must be enabled using morph-factor float sz = static_cast<float>(node.LayerSize()); float l = node.Offset().x / sz, r = (node.Offset().x + 1) / sz; float u = node.Offset().y / sz, d = (node.Offset().y + 1) / sz; vec3 rel_pos = vec3(inverse(GetModelMatrix()) * vec4(viewpoint, 1.0f)); rel_pos.x = ClosestSegmentPoint(rel_pos.x, l, r); rel_pos.y = ClosestSegmentPoint(rel_pos.y, node->heights.x, node->heights.y); rel_pos.z = ClosestSegmentPoint(rel_pos.z, u, d); if (length(rel_pos)*length(rel_pos) / (1.0f + node->heights.y - node->heights.x) / (r - l) / (d - u) > 5.0f || node.Level() == maxLOD) { //This node is probably enabled } else { //This node is not enabled //continue checking its children DisableNodes(node); RenewNodes(viewpoint, node.Child(1)); RenewNodes(viewpoint, node.Child(0)); RenewNodes(viewpoint, node.Child(3)); RenewNodes(viewpoint, node.Child(2)); } }
void Terrain::EnableNodes(const QuadTree<TerrainNode>::Iterator& node) { node->enabled = true; for (int i = 0; i < QTREE_CHILDREN_COUNT; i++) { if (node.Child(i)) EnableNodes(node.Child(i)); } }
void Terrain::UnloadVertices(const QuadTree<TerrainNode>::Iterator& node) { if (node->vaoID) { glBindBuffer(GL_ARRAY_BUFFER, 0); glDeleteBuffers(2, node->vboID); glBindVertexArray(0); glDeleteVertexArrays(1, &node->vaoID); node->vaoID = NULL; } for (int i = 0; i < QTREE_CHILDREN_COUNT; i++) if (node.Child(i)) UnloadVertices(node.Child(i)); }