Fixes up some bounding box stuff
This commit is contained in:
@@ -5,6 +5,7 @@
|
||||
#include "engine/debug/profiling/counters.hpp"
|
||||
#include "engine/math/literals/size.hpp"
|
||||
#include "engine/memory/buffers/Buffer.hpp"
|
||||
#include "engine/tree/octtree/OctTreeNode.hpp"
|
||||
#include "safe_include.hpp"
|
||||
|
||||
namespace fgl::engine::gui
|
||||
@@ -110,6 +111,8 @@ namespace fgl::engine::gui
|
||||
drawMemoryStats();
|
||||
}
|
||||
|
||||
imGuiOctTreeSettings( info );
|
||||
|
||||
ImGui::End();
|
||||
}
|
||||
|
||||
|
||||
@@ -27,11 +27,11 @@ namespace fgl::engine
|
||||
EngineContext::EngineContext() :
|
||||
m_ubo_buffer_pool( 512_KiB, vk::BufferUsageFlagBits::eUniformBuffer, vk::MemoryPropertyFlagBits::eHostVisible ),
|
||||
m_matrix_info_pool(
|
||||
2_MiB,
|
||||
256_MiB,
|
||||
vk::BufferUsageFlagBits::eVertexBuffer,
|
||||
vk::MemoryPropertyFlagBits::eDeviceLocal | vk::MemoryPropertyFlagBits::eHostVisible ),
|
||||
m_draw_parameter_pool(
|
||||
1_MiB,
|
||||
128_MiB,
|
||||
vk::BufferUsageFlagBits::eIndirectBuffer,
|
||||
vk::MemoryPropertyFlagBits::eDeviceLocal | vk::MemoryPropertyFlagBits::eHostVisible ),
|
||||
m_delta_time( 0.0 )
|
||||
|
||||
@@ -4,12 +4,12 @@
|
||||
|
||||
#include "TransferManager.hpp"
|
||||
|
||||
#include "engine/memory/buffers/Buffer.hpp"
|
||||
#include "engine/memory/buffers/BufferSuballocation.hpp"
|
||||
#include "engine/memory/buffers/vector/HostVector.hpp"
|
||||
#include "engine/assets/image/Image.hpp"
|
||||
#include "engine/assets/image/ImageHandle.hpp"
|
||||
#include "engine/math/literals/size.hpp"
|
||||
#include "engine/memory/buffers/Buffer.hpp"
|
||||
#include "engine/memory/buffers/BufferSuballocation.hpp"
|
||||
#include "engine/memory/buffers/vector/HostVector.hpp"
|
||||
#include "engine/texture/Texture.hpp"
|
||||
|
||||
namespace fgl::engine::memory
|
||||
@@ -21,8 +21,14 @@ namespace fgl::engine::memory
|
||||
|
||||
if ( queue.size() > 0 ) log::info( "[TransferManager]: Queue size: {}", queue.size() );
|
||||
|
||||
std::size_t counter { 0 };
|
||||
constexpr std::size_t counter_max { 256 };
|
||||
|
||||
while ( queue.size() > 0 )
|
||||
{
|
||||
++counter;
|
||||
if ( counter > counter_max ) break;
|
||||
|
||||
TransferData data { std::move( queue.front() ) };
|
||||
queue.pop();
|
||||
|
||||
|
||||
@@ -17,6 +17,11 @@ namespace fgl::engine::debug
|
||||
drawLine( line.getStart(), line.getEnd(), color );
|
||||
}
|
||||
|
||||
void drawBoundingBox( const AxisAlignedBoundingBox< CoordinateSpace::World >& bounding_box )
|
||||
{
|
||||
drawBoundingBox( bounding_box, glm::vec3( 1.0f ) );
|
||||
}
|
||||
|
||||
void drawBoundingBox( const AxisAlignedBoundingBox< CoordinateSpace::World >& bounding_box, const glm::vec3 color )
|
||||
{
|
||||
for ( const auto& line : bounding_box.lines() )
|
||||
@@ -27,11 +32,14 @@ namespace fgl::engine::debug
|
||||
|
||||
void drawBoundingBox( const OrientedBoundingBox< CoordinateSpace::World >& bounding_box )
|
||||
{
|
||||
constexpr glm::vec3 bounding_box_color { 1.0f, 0.0f, 0.0f };
|
||||
drawBoundingBox( bounding_box, glm::vec3( 1.0f ) );
|
||||
}
|
||||
|
||||
void drawBoundingBox( const OrientedBoundingBox< CoordinateSpace::World >& bounding_box, const glm::vec3 color )
|
||||
{
|
||||
for ( const auto& line : bounding_box.lines() )
|
||||
{
|
||||
drawLine( line.getStart(), line.getEnd(), bounding_box_color );
|
||||
drawLine( line.getStart(), line.getEnd(), color );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -15,7 +15,11 @@ namespace fgl::engine::debug
|
||||
void drawLine( const LineSegment< CoordinateSpace::World >& line, glm::vec3 color = { 1.0f, 1.0f, 1.0f } );
|
||||
|
||||
void drawBoundingBox( const AxisAlignedBoundingBox< CoordinateSpace::World >& bounding_box );
|
||||
void drawBoundingBox( const AxisAlignedBoundingBox< CoordinateSpace::World >& bounding_box, glm::vec3 color );
|
||||
|
||||
void drawBoundingBox( const OrientedBoundingBox< CoordinateSpace::World >& bounding_box );
|
||||
void drawBoundingBox( const OrientedBoundingBox< CoordinateSpace::World >& bounding_box, glm::vec3 color );
|
||||
|
||||
void drawFrustum( const Frustum& frustum );
|
||||
|
||||
void drawAxisHelper();
|
||||
|
||||
@@ -111,6 +111,31 @@ namespace fgl::engine
|
||||
return *this;
|
||||
}
|
||||
|
||||
template < CoordinateSpace CType >
|
||||
AxisAlignedBoundingBox< CType >& AxisAlignedBoundingBox< CType >::combine( const OrientedBoundingBox< CType >&
|
||||
other )
|
||||
{
|
||||
const auto other_trf { other.topRightForward() };
|
||||
const auto other_blb { other.bottomLeftBack() };
|
||||
|
||||
const Coordinate< CType > new_top_right_forward {
|
||||
std::max( this->m_top_right_forward.x, other_trf.x ),
|
||||
std::max( this->m_top_right_forward.y, other_trf.y ),
|
||||
std::max( this->m_top_right_forward.z, other_trf.z ),
|
||||
};
|
||||
|
||||
const Coordinate< CType > new_bottom_left_back {
|
||||
std::min( this->m_bottom_left_back.x, other_blb.x ),
|
||||
std::min( this->m_bottom_left_back.y, other_blb.y ),
|
||||
std::min( this->m_bottom_left_back.z, other_blb.z ),
|
||||
};
|
||||
|
||||
this->m_top_right_forward = new_top_right_forward;
|
||||
this->m_bottom_left_back = new_bottom_left_back;
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
template < CoordinateSpace CType >
|
||||
AxisAlignedBoundingBox< CType >::AxisAlignedBoundingBox( const OrientedBoundingBox< CType >& oobb ) :
|
||||
m_top_right_forward( constants::DEFAULT_VEC3 ),
|
||||
|
||||
@@ -46,6 +46,8 @@ namespace fgl::engine
|
||||
explicit AxisAlignedBoundingBox( const OrientedBoundingBox< CType >& oobb );
|
||||
|
||||
AxisAlignedBoundingBox& combine( const AxisAlignedBoundingBox& other );
|
||||
AxisAlignedBoundingBox& combine( const OrientedBoundingBox< CType >& other );
|
||||
|
||||
//AxisAlignedBoundingBox& combine( const OrientedBoundingBox< CType >& other );
|
||||
|
||||
bool operator==( const AxisAlignedBoundingBox< CType >& other ) const
|
||||
|
||||
@@ -33,6 +33,11 @@ namespace fgl::engine
|
||||
constexpr NormalVector up() const { return NormalVector( constants::WORLD_Z ); }
|
||||
|
||||
constexpr NormalVector forward() const { return NormalVector( constants::WORLD_Y ); }
|
||||
|
||||
operator AxisAlignedBoundingBox< CType >() const
|
||||
{
|
||||
return static_cast< AxisAlignedBoundingBox< CType > >( *this );
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace fgl::engine
|
||||
|
||||
@@ -200,7 +200,7 @@ namespace fgl::engine
|
||||
}
|
||||
|
||||
template < CoordinateSpace CType >
|
||||
AxisAlignedBoundingBox< CType > OrientedBoundingBox< CType >::alignToWorld()
|
||||
AxisAlignedBoundingBox< CType > OrientedBoundingBox< CType >::alignToWorld() const
|
||||
{
|
||||
const auto points { this->points() };
|
||||
glm::vec3 max { std::numeric_limits< glm::vec3::type >::infinity() };
|
||||
|
||||
@@ -110,7 +110,7 @@ namespace fgl::engine
|
||||
|
||||
OrientedBoundingBox combine( const OrientedBoundingBox& other ) const;
|
||||
|
||||
AxisAlignedBoundingBox< CType > alignToWorld();
|
||||
AxisAlignedBoundingBox< CType > alignToWorld() const;
|
||||
};
|
||||
|
||||
template < CoordinateSpace CType, MatrixType MType >
|
||||
|
||||
@@ -96,11 +96,25 @@ namespace fgl::engine
|
||||
template < CoordinateSpace CType >
|
||||
Coordinate< CType > midpoint( const Coordinate< CType > left, const Coordinate< CType > right )
|
||||
{
|
||||
glm::vec3 left_vec { left.vec() };
|
||||
glm::vec3 right_vec { right.vec() };
|
||||
|
||||
left_vec *= 0.5f;
|
||||
right_vec *= 0.5f;
|
||||
|
||||
return Coordinate< CType >( left_vec + right_vec );
|
||||
|
||||
/*
|
||||
const auto x { ( left.vec().x + right.vec().x ) / 2.0f };
|
||||
const auto y { ( left.vec().y + right.vec().y ) / 2.0f };
|
||||
const auto z { ( left.vec().z + right.vec().z ) / 2.0f };
|
||||
|
||||
assert( !std::isinf( x ) );
|
||||
assert( !std::isinf( y ) );
|
||||
assert( !std::isinf( z ) );
|
||||
|
||||
return Coordinate< CType >( x, y, z );
|
||||
*/
|
||||
}
|
||||
|
||||
} // namespace fgl::engine
|
||||
|
||||
@@ -84,7 +84,7 @@ namespace fgl::engine
|
||||
std::make_pair( matrix_info.albedo_id, primitive.m_index_buffer.getOffset() )
|
||||
};
|
||||
|
||||
debug::drawBoundingBox( matrix * primitive.m_bounding_box );
|
||||
//debug::drawBoundingBox( matrix * primitive.m_bounding_box );
|
||||
|
||||
assert( primitive.m_index_buffer.size() > 0 );
|
||||
|
||||
|
||||
@@ -8,7 +8,11 @@
|
||||
#include <engine/FrameInfo.hpp>
|
||||
#include <glm/gtx/string_cast.hpp>
|
||||
|
||||
#include <imgui.h>
|
||||
|
||||
#include "engine/assets/model/Model.hpp"
|
||||
#include "engine/clock.hpp"
|
||||
#include "engine/debug/drawers.hpp"
|
||||
#include "engine/primitives/Frustum.hpp"
|
||||
|
||||
namespace fgl::engine
|
||||
@@ -18,18 +22,19 @@ namespace fgl::engine
|
||||
static bool draw_leaf_fit_bounds { false };
|
||||
static bool draw_leaf_real_bounds { false };
|
||||
static bool draw_inview_bounds { false };
|
||||
static bool draw_branches { false };
|
||||
static std::size_t number_moved { 0 };
|
||||
static std::optional< std::chrono::microseconds > time { std::nullopt };
|
||||
|
||||
void imGuiOctTreeSettings( FrameInfo& info )
|
||||
void imGuiOctTreeSettings( const FrameInfo& info )
|
||||
{
|
||||
/*
|
||||
#if ENABLE_IMGUI
|
||||
if ( ImGui::CollapsingHeader( "OctTree debug settings" ) )
|
||||
{
|
||||
ImGui::Checkbox( "Draw leaf fitted bounding boxes", &draw_leaf_fit_bounds );
|
||||
ImGui::Checkbox( "Draw leaf real bounding boxes", &draw_leaf_real_bounds );
|
||||
ImGui::Checkbox( "Draw ALL in view bounding boxes", &draw_inview_bounds );
|
||||
ImGui::Checkbox( "Draw branches", &draw_branches );
|
||||
|
||||
if ( ImGui::Button( "Reorganize Octtree" ) )
|
||||
{
|
||||
@@ -40,30 +45,39 @@ namespace fgl::engine
|
||||
time = std::chrono::duration_cast< std::chrono::microseconds >( time_diff );
|
||||
}
|
||||
|
||||
if ( ImGui::Button( "Recalculate Bounds" ) )
|
||||
{
|
||||
const auto start { fgl::clock::now() };
|
||||
info.game_objects.recalculateBounds();
|
||||
const auto end { fgl::clock::now() };
|
||||
const auto time_diff { end - start };
|
||||
time = std::chrono::duration_cast< std::chrono::microseconds >( time_diff );
|
||||
}
|
||||
|
||||
if ( time.has_value() )
|
||||
{
|
||||
ImGui::Text( "Time spent reorganizing: %.2ldus", time.value().count() );
|
||||
ImGui::Text( "Moved %ld objects", number_moved );
|
||||
}
|
||||
}
|
||||
#endif*/
|
||||
#endif
|
||||
}
|
||||
|
||||
void OctTreeNode::getAllLeafsInFrustum( const Frustum& frustum, std::vector< OctTreeNodeLeaf* >& out_leafs )
|
||||
{
|
||||
ZoneScoped;
|
||||
//Check if we are inside of the frustum.
|
||||
if ( !isInFrustum( frustum ) ) return;
|
||||
|
||||
auto& leafs { out_leafs };
|
||||
leafs.reserve( 256 );
|
||||
|
||||
switch ( m_node_data.index() )
|
||||
{
|
||||
case 0: // NodeArray
|
||||
{
|
||||
//Check if we are inside the frustum.
|
||||
if ( !isInFrustum( frustum ) ) return;
|
||||
|
||||
assert( std::holds_alternative< OctTreeNodeArray >( m_node_data ) );
|
||||
OctTreeNodeArray& node_array { std::get< OctTreeNodeArray >( m_node_data ) };
|
||||
const OctTreeNodeArray& node_array { std::get< OctTreeNodeArray >( m_node_data ) };
|
||||
//Search deeper
|
||||
|
||||
node_array[ LEFT ][ FORWARD ][ TOP ]->getAllLeafsInFrustum( frustum, out_leafs );
|
||||
@@ -81,8 +95,13 @@ namespace fgl::engine
|
||||
}
|
||||
case 1: // NodeLeaf
|
||||
{
|
||||
assert( std::holds_alternative< OctTreeNodeLeaf >( m_node_data ) );
|
||||
OctTreeNodeLeaf& leaf { std::get< OctTreeNodeLeaf >( m_node_data ) };
|
||||
if ( leaf.size() == 0 ) return;
|
||||
|
||||
//Check if we are inside the frustum.
|
||||
if ( !isInFrustum( frustum ) ) return;
|
||||
|
||||
assert( std::holds_alternative< OctTreeNodeLeaf >( m_node_data ) );
|
||||
leafs.emplace_back( &leaf );
|
||||
|
||||
//debug::world::drawBoundingBox( m_bounds );
|
||||
@@ -104,18 +123,22 @@ namespace fgl::engine
|
||||
OctTreeNode& OctTreeNode::operator[]( const WorldCoordinate coord )
|
||||
{
|
||||
assert( std::holds_alternative< OctTreeNodeArray >( m_node_data ) );
|
||||
const auto test_dim { glm::greaterThanEqual( coord.vec(), this->m_bounds.getPosition().vec() ) };
|
||||
|
||||
const auto bounds_center { this->m_bounds.getPosition().vec() };
|
||||
|
||||
const auto test_dim { glm::greaterThanEqual( coord.vec(), bounds_center ) };
|
||||
|
||||
auto& node_array { std::get< OctTreeNodeArray >( m_node_data ) };
|
||||
const auto& node { node_array[ test_dim.x ][ test_dim.y ][ test_dim.z ] };
|
||||
const auto& node { node_array[ test_dim.x ? 1 : 0 ][ test_dim.y ? 1 : 0 ][ test_dim.z ? 1 : 0 ] };
|
||||
assert( node );
|
||||
assert( node->canContain( coord ) );
|
||||
|
||||
return *node.get();
|
||||
}
|
||||
|
||||
OctTreeNode::OctTreeNode( const WorldCoordinate center, float span, OctTreeNode* parent ) :
|
||||
m_fit_bounding_box( center, glm::vec3( span, span, span ) ),
|
||||
m_bounds( center, span ),
|
||||
OctTreeNode::OctTreeNode( const WorldCoordinate center, const float span, OctTreeNode* parent ) :
|
||||
m_fit_bounding_box( center, glm::vec3( glm::abs( span ) ) ),
|
||||
m_bounds( center, glm::abs( span ) ),
|
||||
m_node_data( OctTreeNodeLeaf() ),
|
||||
m_parent( parent )
|
||||
{
|
||||
@@ -123,11 +146,11 @@ namespace fgl::engine
|
||||
std::get< OctTreeNodeLeaf >( m_node_data ).reserve( MAX_NODES_IN_LEAF );
|
||||
}
|
||||
|
||||
void OctTreeNode::split( int depth )
|
||||
void OctTreeNode::split( const int depth )
|
||||
{
|
||||
ZoneScoped;
|
||||
if ( std::holds_alternative< OctTreeNodeArray >( m_node_data ) ) return;
|
||||
auto& game_objects { std::get< OctTreeNodeLeaf >( m_node_data ) };
|
||||
auto game_objects { std::get< OctTreeNodeLeaf >( std::move( m_node_data ) ) };
|
||||
|
||||
//Figure out the half span
|
||||
const float half_span { m_bounds.span() / 2.0f };
|
||||
@@ -139,11 +162,17 @@ namespace fgl::engine
|
||||
const float left_x { center.x - half_span };
|
||||
const float right_x { center.x + half_span };
|
||||
|
||||
const float forward_y { center.y - half_span };
|
||||
const float backward_y { center.y + half_span };
|
||||
const float forward_y { center.y + half_span };
|
||||
const float backward_y { center.y - half_span };
|
||||
|
||||
const float top_z { center.z - half_span };
|
||||
const float bottom_z { center.z + half_span };
|
||||
const float top_z { center.z + half_span };
|
||||
const float bottom_z { center.z - half_span };
|
||||
|
||||
assert( !std::isinf( left_x ) && !std::isinf( right_x ) );
|
||||
assert( !std::isinf( forward_y ) && !std::isinf( backward_y ) );
|
||||
assert( !std::isinf( top_z ) && !std::isinf( bottom_z ) );
|
||||
|
||||
log::debug( "Splitting node at {}", m_bounds.span() );
|
||||
|
||||
new_nodes[ LEFT ][ FORWARD ][ TOP ] =
|
||||
std::make_unique< OctTreeNode >( WorldCoordinate( left_x, forward_y, top_z ), half_span, this );
|
||||
@@ -195,7 +224,8 @@ namespace fgl::engine
|
||||
OctTreeNode* OctTreeNode::addGameObject( GameObject&& obj )
|
||||
{
|
||||
assert( this->canContain( obj ) );
|
||||
if ( std::holds_alternative< OctTreeNodeLeaf >( m_node_data ) )
|
||||
|
||||
if ( std::holds_alternative< OctTreeNodeLeaf >( m_node_data ) ) // This node is a leaf
|
||||
{
|
||||
auto& objects { std::get< OctTreeNodeLeaf >( m_node_data ) };
|
||||
assert( objects.capacity() == MAX_NODES_IN_LEAF );
|
||||
@@ -203,15 +233,21 @@ namespace fgl::engine
|
||||
if ( objects.size() + 1 > MAX_NODES_IN_LEAF )
|
||||
{
|
||||
split();
|
||||
return this->addGameObject( std::move( obj ) );
|
||||
auto* node { this->addGameObject( std::move( obj ) ) };
|
||||
return node;
|
||||
}
|
||||
|
||||
log::debug( "Added game object" );
|
||||
objects.emplace_back( std::move( obj ) );
|
||||
return this;
|
||||
}
|
||||
else if ( std::holds_alternative< OctTreeNodeArray >( m_node_data ) )
|
||||
{
|
||||
auto* node { ( *this )[ obj.getPosition() ].addGameObject( std::forward< GameObject >( obj ) ) };
|
||||
return node;
|
||||
}
|
||||
|
||||
return ( *this )[ obj.getPosition() ].addGameObject( std::forward< GameObject >( obj ) );
|
||||
FGL_UNREACHABLE();
|
||||
}
|
||||
|
||||
bool OctTreeNode::isInFrustum( const Frustum& frustum ) const
|
||||
@@ -219,10 +255,22 @@ namespace fgl::engine
|
||||
#if ENABLE_IMGUI
|
||||
if ( !isEmpty() && frustum.intersects( m_fit_bounding_box ) )
|
||||
{
|
||||
if ( ( draw_inview_bounds || std::holds_alternative< OctTreeNodeLeaf >( this->m_node_data ) ) && m_parent )
|
||||
if ( ( draw_inview_bounds || ( std::holds_alternative< OctTreeNodeLeaf >( this->m_node_data ) )
|
||||
|| draw_branches )
|
||||
&& m_parent ) [[unlikely]]
|
||||
{
|
||||
// if ( draw_leaf_fit_bounds ) debug::world::drawBoundingBox( m_fit_bounding_box );
|
||||
// if ( draw_leaf_real_bounds ) debug::world::drawBoundingBox( m_bounds );
|
||||
if ( draw_leaf_fit_bounds ) [[unlikely]]
|
||||
debug::drawBoundingBox( m_fit_bounding_box );
|
||||
/*
|
||||
debug::drawBoundingBox(
|
||||
m_fit_bounding_box,
|
||||
glm::vec3(
|
||||
m_fit_bounding_box.getPosition().x > 0.0f ? 1.0f : 0.0f,
|
||||
m_fit_bounding_box.getPosition().y > 0.0f ? 1.0f : 0.0f,
|
||||
m_fit_bounding_box.getPosition().z > 0.0f ? 1.0f : 0.0f ) );
|
||||
*/
|
||||
if ( draw_leaf_real_bounds ) [[unlikely]]
|
||||
debug::drawBoundingBox( m_bounds );
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -235,6 +283,49 @@ namespace fgl::engine
|
||||
#endif
|
||||
}
|
||||
|
||||
void OctTreeNode::recalculateBounds()
|
||||
{
|
||||
m_fit_bounding_box = m_bounds;
|
||||
|
||||
if ( std::holds_alternative< NodeDataT >( m_node_data ) )
|
||||
{
|
||||
// We aren't a leaf. So we need to use the bounding box of the children below us
|
||||
|
||||
const auto& nodes { std::get< NodeDataT >( m_node_data ) };
|
||||
|
||||
for ( std::size_t x = 0; x < 2; ++x )
|
||||
{
|
||||
for ( std::size_t y = 0; y < 2; ++y )
|
||||
{
|
||||
for ( std::size_t z = 0; z < 2; ++z )
|
||||
{
|
||||
nodes[ x ][ y ][ z ]->recalculateBounds();
|
||||
m_fit_bounding_box = m_fit_bounding_box.combine( nodes[ x ][ y ][ z ]->m_fit_bounding_box );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if ( std::holds_alternative< LeafDataT >( m_node_data ) )
|
||||
{
|
||||
const auto& data { std::get< LeafDataT >( m_node_data ) };
|
||||
|
||||
for ( const auto& game_object : data )
|
||||
{
|
||||
auto model_components { game_object.getComponents< ModelComponent >() };
|
||||
|
||||
for ( const auto& model : model_components )
|
||||
{
|
||||
const OrientedBoundingBox model_bounding_box { ( *model )->getBoundingBox() };
|
||||
|
||||
const OrientedBoundingBox< CoordinateSpace::World > world_bounding_box { model->m_transform.mat()
|
||||
* model_bounding_box };
|
||||
|
||||
m_fit_bounding_box = m_fit_bounding_box.combine( world_bounding_box.alignToWorld() );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
OctTreeNode* OctTreeNode::findID( const GameObject::GameObjectID id )
|
||||
{
|
||||
ZoneScoped;
|
||||
@@ -286,9 +377,14 @@ namespace fgl::engine
|
||||
game_objects.begin(), game_objects.end(), [ id ]( const GameObject& obj ) { return id == obj.getId(); } );
|
||||
}
|
||||
|
||||
bool OctTreeNode::canContain( const GameObject& obj )
|
||||
bool OctTreeNode::canContain( const GameObject& obj ) const
|
||||
{
|
||||
return m_bounds.contains( obj.getTransform().translation );
|
||||
return canContain( obj.getTransform().translation );
|
||||
}
|
||||
|
||||
bool OctTreeNode::canContain( const WorldCoordinate& obj ) const
|
||||
{
|
||||
return m_bounds.contains( obj );
|
||||
}
|
||||
|
||||
GameObject OctTreeNode::extract( const GameObject::GameObjectID id )
|
||||
@@ -422,6 +518,25 @@ namespace fgl::engine
|
||||
std::size_t OctTreeNode::reorganize()
|
||||
{
|
||||
std::size_t counter { 0 };
|
||||
if ( std::holds_alternative< NodeDataT >( m_node_data ) )
|
||||
{
|
||||
const auto& nodes { std::get< NodeDataT >( m_node_data ) };
|
||||
|
||||
for ( std::size_t x = 0; x < 2; ++x )
|
||||
{
|
||||
for ( std::size_t y = 0; y < 2; ++y )
|
||||
{
|
||||
for ( std::size_t z = 0; z < 2; ++z )
|
||||
{
|
||||
if ( x == 0 && y == 0 && z == 0 ) continue;
|
||||
const auto& node { nodes[ x ][ y ][ z ] };
|
||||
counter += node->reorganize();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return counter;
|
||||
}
|
||||
if ( std::holds_alternative< LeafDataT >( m_node_data ) )
|
||||
{
|
||||
//Check if any of the nodes in this group need to be moved.
|
||||
@@ -441,25 +556,6 @@ namespace fgl::engine
|
||||
}
|
||||
return counter;
|
||||
}
|
||||
else if ( std::holds_alternative< NodeDataT >( m_node_data ) )
|
||||
{
|
||||
const auto& nodes { std::get< NodeDataT >( m_node_data ) };
|
||||
|
||||
for ( std::size_t x = 0; x < 2; ++x )
|
||||
{
|
||||
for ( std::size_t y = 0; y < 2; ++y )
|
||||
{
|
||||
for ( std::size_t z = 0; z < 2; ++z )
|
||||
{
|
||||
if ( x == 0 && y == 0 && z == 0 ) continue;
|
||||
const auto& node { nodes[ x ][ y ][ z ] };
|
||||
counter += node->reorganize();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return counter;
|
||||
}
|
||||
|
||||
FGL_UNREACHABLE();
|
||||
}
|
||||
|
||||
@@ -14,17 +14,19 @@
|
||||
namespace fgl::engine
|
||||
{
|
||||
constexpr std::size_t MAX_NODES_IN_LEAF { 32 };
|
||||
constexpr std::size_t STARTING_DEPTH { 4 };
|
||||
constexpr std::size_t STARTING_DEPTH { 1 };
|
||||
constexpr float ROOT_SPAN { std::numeric_limits< float >::max() };
|
||||
|
||||
struct Frustum;
|
||||
|
||||
constexpr std::uint8_t TOP { 0 };
|
||||
constexpr std::uint8_t BOTTOM { 1 };
|
||||
constexpr std::uint8_t LEFT { 0 };
|
||||
constexpr std::uint8_t TOP { 1 };
|
||||
constexpr std::uint8_t BOTTOM { 0 };
|
||||
|
||||
constexpr std::uint8_t RIGHT { 1 };
|
||||
constexpr std::uint8_t FORWARD { 0 };
|
||||
constexpr std::uint8_t BACK { 1 };
|
||||
constexpr std::uint8_t LEFT { 0 };
|
||||
|
||||
constexpr std::uint8_t FORWARD { 1 };
|
||||
constexpr std::uint8_t BACK { 0 };
|
||||
|
||||
class OctTreeNode;
|
||||
class GameObject;
|
||||
@@ -37,7 +39,7 @@ namespace fgl::engine
|
||||
|
||||
struct FrameInfo;
|
||||
|
||||
void imGuiOctTreeSettings( FrameInfo& info );
|
||||
void imGuiOctTreeSettings( const FrameInfo& info );
|
||||
|
||||
class OctTreeNode
|
||||
{
|
||||
@@ -79,7 +81,8 @@ namespace fgl::engine
|
||||
OctTreeNode* getRoot();
|
||||
|
||||
//! returns true if this node should contain the given object
|
||||
bool canContain( const GameObject& obj );
|
||||
bool canContain( const GameObject& obj ) const;
|
||||
bool canContain( const WorldCoordinate& obj ) const;
|
||||
|
||||
GameObject extract( GameObject::GameObjectID id );
|
||||
|
||||
@@ -107,6 +110,8 @@ namespace fgl::engine
|
||||
//! Rebuilds the tree checking if nodes have moved.
|
||||
std::size_t reorganize();
|
||||
|
||||
void recalculateBounds();
|
||||
|
||||
constexpr static std::size_t LEAF_RESERVE_SIZE { 1024 };
|
||||
|
||||
[[nodiscard]] std::vector< OctTreeNodeLeaf* > getAllLeafs()
|
||||
|
||||
Reference in New Issue
Block a user