Graphics/GraphicalMesh: Allow to update submeshes

This commit is contained in:
SirLynix 2022-06-16 18:19:48 +02:00
parent 2cc4944f58
commit 62ba4f172b
8 changed files with 73 additions and 25 deletions

View File

@ -109,7 +109,7 @@ int main()
return __LINE__;
}
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = std::make_shared<Nz::GraphicalMesh>(*spaceship);
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = Nz::GraphicalMesh::BuildFromMesh(*spaceship);
Nz::TextureParams texParams;
texParams.renderDevice = device;
@ -125,7 +125,7 @@ int main()
//planeMesh->BuildSubMesh(Nz::Primitive::Cone(1.f, 1.f, 16, Nz::Matrix4f::Rotate(Nz::EulerAnglesf(90.f, 0.f, 0.f))), planeParams);
planeMesh->SetMaterialCount(1);
std::shared_ptr<Nz::GraphicalMesh> planeMeshGfx = std::make_shared<Nz::GraphicalMesh>(*planeMesh);
std::shared_ptr<Nz::GraphicalMesh> planeMeshGfx = Nz::GraphicalMesh::BuildFromMesh(*planeMesh);
// Skybox
meshPrimitiveParams.vertexDeclaration = Nz::VertexDeclaration::Get(Nz::VertexLayout::XYZ);
@ -135,7 +135,7 @@ int main()
cubeMesh->BuildSubMesh(Nz::Primitive::Box(Nz::Vector3f::Unit(), Nz::Vector3ui(0), Nz::Matrix4f::Scale({ 1.f, -1.f, 1.f })), meshPrimitiveParams);
cubeMesh->SetMaterialCount(1);
std::shared_ptr<Nz::GraphicalMesh> cubeMeshGfx = std::make_shared<Nz::GraphicalMesh>(*cubeMesh);
std::shared_ptr<Nz::GraphicalMesh> cubeMeshGfx = Nz::GraphicalMesh::BuildFromMesh(*cubeMesh);
Nz::RenderPipelineLayoutInfo skyboxPipelineLayoutInfo;
skyboxPipelineLayoutInfo.bindings.push_back({
@ -187,7 +187,7 @@ int main()
coneMesh->BuildSubMesh(Nz::Primitive::Cone(1.f, 1.f, 16, Nz::Matrix4f::Rotate(Nz::EulerAnglesf(90.f, 0.f, 0.f))), meshPrimitiveParams);
coneMesh->SetMaterialCount(1);
std::shared_ptr<Nz::GraphicalMesh> coneMeshGfx = std::make_shared<Nz::GraphicalMesh>(*coneMesh);
std::shared_ptr<Nz::GraphicalMesh> coneMeshGfx = Nz::GraphicalMesh::BuildFromMesh(*coneMesh);
auto customSettings = Nz::BasicMaterial::GetSettings()->GetBuilderData();
customSettings.shaders.clear();
@ -572,8 +572,6 @@ int main()
std::shared_ptr<Nz::ShaderBinding> godRaysBlitShaderBinding;
const std::shared_ptr<const Nz::VertexDeclaration>& lightingVertexDeclaration = Nz::VertexDeclaration::Get(Nz::VertexLayout::XYZ_UV);
std::shared_ptr<Nz::RenderPipeline> fullscreenPipeline = device->InstantiateRenderPipeline(fullscreenPipelineInfo);
Nz::RenderPipelineInfo lightingPipelineInfo;
@ -1201,8 +1199,8 @@ int main()
case Nz::WindowEventType::Resized:
{
Nz::Vector2ui windowSize = window.GetSize();
viewerInstance.UpdateProjectionMatrix(Nz::Matrix4f::Perspective(Nz::DegreeAnglef(70.f), float(windowSize.x) / windowSize.y, 0.1f, 1000.f));
Nz::Vector2ui newSize = window.GetSize();
viewerInstance.UpdateProjectionMatrix(Nz::Matrix4f::Perspective(Nz::DegreeAnglef(70.f), float(newSize.x) / newSize.y, 0.1f, 1000.f));
break;
}

View File

@ -46,7 +46,7 @@ int main()
return __LINE__;
}
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = std::make_shared<Nz::GraphicalMesh>(*spaceshipMesh);
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = Nz::GraphicalMesh::BuildFromMesh(*spaceshipMesh);
// Texture
std::shared_ptr<Nz::Image> diffuseImage = Nz::Image::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png");

View File

@ -61,7 +61,7 @@ int main()
}
const Nz::Boxf& spaceshipAABB = spaceshipMesh->GetAABB();
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = std::make_shared<Nz::GraphicalMesh>(*spaceshipMesh);
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = Nz::GraphicalMesh::BuildFromMesh(*spaceshipMesh);
// Texture
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>();
@ -151,7 +151,7 @@ int main()
std::shared_ptr<Nz::Model> colliderModel;
{
std::shared_ptr<Nz::Mesh> colliderMesh = Nz::Mesh::Build(shipCollider->GenerateMesh());
std::shared_ptr<Nz::GraphicalMesh> colliderGraphicalMesh = std::make_shared<Nz::GraphicalMesh>(*colliderMesh);
std::shared_ptr<Nz::GraphicalMesh> colliderGraphicalMesh = Nz::GraphicalMesh::BuildFromMesh(*colliderMesh);
colliderModel = std::make_shared<Nz::Model>(colliderGraphicalMesh, spaceshipAABB);
for (std::size_t i = 0; i < colliderModel->GetSubMeshCount(); ++i)

View File

@ -8,6 +8,7 @@
#define NAZARA_GRAPHICS_GRAPHICALMESH_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Utils/Signal.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Renderer/RenderBuffer.hpp>
#include <Nazara/Utility/Mesh.hpp>
@ -19,32 +20,44 @@ namespace Nz
class NAZARA_GRAPHICS_API GraphicalMesh
{
public:
GraphicalMesh(const Mesh& mesh);
struct SubMesh;
GraphicalMesh() = default;
GraphicalMesh(const GraphicalMesh&) = delete;
GraphicalMesh(GraphicalMesh&&) noexcept = default;
~GraphicalMesh() = default;
inline std::size_t AddSubMesh(SubMesh subMesh);
inline void Clear();
inline const std::shared_ptr<RenderBuffer>& GetIndexBuffer(std::size_t subMesh) const;
inline std::size_t GetIndexCount(std::size_t subMesh) const;
inline UInt32 GetIndexCount(std::size_t subMesh) const;
inline IndexType GetIndexType(std::size_t subMesh) const;
inline const std::shared_ptr<RenderBuffer>& GetVertexBuffer(std::size_t subMesh) const;
inline const std::shared_ptr<const VertexDeclaration>& GetVertexDeclaration(std::size_t subMesh) const;
inline std::size_t GetSubMeshCount() const;
GraphicalMesh& operator=(const GraphicalMesh&) = delete;
GraphicalMesh& operator=(GraphicalMesh&&) noexcept = default;
inline void UpdateSubMeshIndexCount(std::size_t subMeshIndex, UInt32 indexCount);
private:
struct GraphicalSubMesh
GraphicalMesh& operator=(const GraphicalMesh&) = delete;
GraphicalMesh& operator=(GraphicalMesh&&) = delete;
struct SubMesh
{
std::shared_ptr<RenderBuffer> indexBuffer;
std::shared_ptr<RenderBuffer> vertexBuffer;
std::size_t indexCount;
std::shared_ptr<const VertexDeclaration> vertexDeclaration;
IndexType indexType;
UInt32 indexCount;
};
std::vector<GraphicalSubMesh> m_subMeshes;
static std::shared_ptr<GraphicalMesh> BuildFromMesh(const Mesh& mesh);
NazaraSignal(OnInvalidated, GraphicalMesh* /*gfxMesh*/);
private:
std::vector<SubMesh> m_subMeshes;
};
}

View File

@ -8,13 +8,30 @@
namespace Nz
{
inline std::size_t GraphicalMesh::AddSubMesh(SubMesh subMesh)
{
std::size_t subMeshIndex = m_subMeshes.size();
m_subMeshes.emplace_back(std::move(subMesh));
OnInvalidated(this);
return subMeshIndex;
}
inline void GraphicalMesh::Clear()
{
m_subMeshes.clear();
OnInvalidated(this);
}
inline const std::shared_ptr<RenderBuffer>& GraphicalMesh::GetIndexBuffer(std::size_t subMesh) const
{
assert(subMesh < m_subMeshes.size());
return m_subMeshes[subMesh].indexBuffer;
}
inline std::size_t GraphicalMesh::GetIndexCount(std::size_t subMesh) const
inline UInt32 GraphicalMesh::GetIndexCount(std::size_t subMesh) const
{
assert(subMesh < m_subMeshes.size());
return m_subMeshes[subMesh].indexCount;
@ -42,6 +59,14 @@ namespace Nz
{
return m_subMeshes.size();
}
inline void GraphicalMesh::UpdateSubMeshIndexCount(std::size_t subMeshIndex, UInt32 indexCount)
{
NazaraAssert(subMeshIndex < m_subMeshes.size(), "invalid submesh index");
m_subMeshes[subMeshIndex].indexCount = indexCount;
OnInvalidated(this);
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -9,6 +9,7 @@
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/GraphicalMesh.hpp>
#include <Nazara/Graphics/InstancedRenderable.hpp>
#include <Nazara/Renderer/RenderPipeline.hpp>
#include <Nazara/Utility/Mesh.hpp>
@ -17,7 +18,6 @@
namespace Nz
{
class GraphicalMesh;
class Material;
class NAZARA_GRAPHICS_API Model : public InstancedRenderable
@ -50,6 +50,8 @@ namespace Nz
std::vector<RenderPipelineInfo::VertexBufferData> vertexBufferData;
};
NazaraSlot(GraphicalMesh, OnInvalidated, m_onInvalidated);
std::shared_ptr<GraphicalMesh> m_graphicalMesh;
std::vector<SubMeshData> m_submeshes;
Recti m_scissorBox;

View File

@ -11,16 +11,17 @@
namespace Nz
{
GraphicalMesh::GraphicalMesh(const Mesh& mesh)
std::shared_ptr<GraphicalMesh> GraphicalMesh::BuildFromMesh(const Mesh& mesh)
{
assert(mesh.GetAnimationType() == AnimationType::Static);
const std::shared_ptr<RenderDevice>& renderDevice = Graphics::Instance()->GetRenderDevice();
m_subMeshes.reserve(mesh.GetSubMeshCount());
std::shared_ptr<GraphicalMesh> gfxMesh = std::make_shared<GraphicalMesh>();
for (std::size_t i = 0; i < mesh.GetSubMeshCount(); ++i)
{
const SubMesh& subMesh = *mesh.GetSubMesh(i);
const Nz::SubMesh& subMesh = *mesh.GetSubMesh(i);
const StaticMesh& staticMesh = static_cast<const StaticMesh&>(subMesh);
@ -33,7 +34,7 @@ namespace Nz
assert(vertexBuffer->GetBuffer()->GetStorage() == DataStorage::Software);
const SoftwareBuffer* vertexBufferContent = static_cast<const SoftwareBuffer*>(vertexBuffer->GetBuffer().get());
auto& submeshData = m_subMeshes.emplace_back();
GraphicalMesh::SubMesh submeshData;
submeshData.indexBuffer = renderDevice->InstantiateBuffer(BufferType::Index, indexBuffer->GetStride() * indexBuffer->GetIndexCount(), BufferUsage::DeviceLocal | BufferUsage::Write);
if (!submeshData.indexBuffer->Fill(indexBufferContent->GetData() + indexBuffer->GetStartOffset(), 0, indexBuffer->GetEndOffset() - indexBuffer->GetStartOffset()))
throw std::runtime_error("failed to fill index buffer");
@ -46,6 +47,10 @@ namespace Nz
throw std::runtime_error("failed to fill vertex buffer");
submeshData.vertexDeclaration = vertexBuffer->GetVertexDeclaration();
gfxMesh->AddSubMesh(std::move(submeshData));
}
return gfxMesh;
}
}

View File

@ -29,6 +29,11 @@ namespace Nz
};
}
m_onInvalidated.Connect(m_graphicalMesh->OnInvalidated, [this](GraphicalMesh*)
{
OnElementInvalidated(this);
});
UpdateAABB(aabb);
}