Refactor material system (#382)

This commit is contained in:
Jérôme Leclercq 2022-10-31 19:53:41 +01:00 committed by GitHub
parent 0a8048809c
commit dc6ce8427c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
156 changed files with 3633 additions and 4569 deletions

View File

@ -9,20 +9,29 @@ option HasAlphaTexture: bool = false;
option AlphaTest: bool = false; option AlphaTest: bool = false;
[layout(std140)] [layout(std140)]
struct BasicSettings struct MaterialSettings
{ {
[tag("AlphaTestThreshold")]
AlphaThreshold: f32, AlphaThreshold: f32,
[tag("BaseColor")]
BaseColor: vec4[f32] BaseColor: vec4[f32]
} }
[tag("Material")]
external external
{ {
[binding(0)] settings: uniform[BasicSettings], [tag("Settings"), binding(0)] settings: uniform[MaterialSettings],
[binding(1)] MaterialBaseColorMap: sampler2D[f32], [tag("BaseColorMap"), binding(1)] MaterialBaseColorMap: sampler2D[f32],
[binding(2)] MaterialAlphaMap: sampler2D[f32], [tag("AlphaMap"), binding(2)] MaterialAlphaMap: sampler2D[f32],
[binding(3)] TextureOverlay: sampler2D[f32], }
[binding(4)] instanceData: uniform[InstanceData],
[binding(5)] viewerData: uniform[ViewerData], [tag("Engine")]
external
{
[tag("TextureOverlay"), binding(3)] TextureOverlay: sampler2D[f32],
[tag("InstanceData"), binding(4)] instanceData: uniform[InstanceData],
[tag("ViewerData"), binding(5)] viewerData: uniform[ViewerData],
} }
struct InputData struct InputData

View File

@ -5,17 +5,29 @@ import InstanceData from Engine.InstanceData;
import ViewerData from Engine.ViewerData; import ViewerData from Engine.ViewerData;
[layout(std140)] [layout(std140)]
struct BasicSettings struct MaterialSettings
{ {
[tag("AlphaTestThreshold")]
AlphaThreshold: f32, AlphaThreshold: f32,
[tag("BaseColor")]
BaseColor: vec4[f32] BaseColor: vec4[f32]
} }
[tag("Material")]
external external
{ {
[binding(0)] settings: uniform[BasicSettings], [tag("Settings"), binding(0)] settings: uniform[MaterialSettings],
[binding(4)] instanceData: uniform[InstanceData], [tag("BaseColorMap"), binding(1)] MaterialBaseColorMap: sampler2D[f32],
[binding(5)] viewerData: uniform[ViewerData], [tag("AlphaMap"), binding(2)] MaterialAlphaMap: sampler2D[f32],
}
[tag("Engine")]
external
{
[tag("TextureOverlay"), binding(3)] TextureOverlay: sampler2D[f32],
[tag("InstanceData"), binding(4)] instanceData: uniform[InstanceData],
[tag("ViewerData"), binding(5)] viewerData: uniform[ViewerData],
} }
struct InputData struct InputData

View File

@ -192,60 +192,49 @@ int main()
std::shared_ptr<Nz::GraphicalMesh> coneMeshGfx = Nz::GraphicalMesh::BuildFromMesh(*coneMesh); std::shared_ptr<Nz::GraphicalMesh> coneMeshGfx = Nz::GraphicalMesh::BuildFromMesh(*coneMesh);
auto customSettings = Nz::BasicMaterial::GetSettings()->GetBuilderData(); Nz::MaterialSettings settings;
customSettings.shaders.clear(); Nz::PredefinedMaterials::AddBasicSettings(settings);
customSettings.shaders.emplace_back(std::make_shared<Nz::UberShader>(nzsl::ShaderStageType::Fragment, nzsl::ParseFromFile(shaderDir / "deferred_frag.nzsl")));
customSettings.shaders.emplace_back(std::make_shared<Nz::UberShader>(nzsl::ShaderStageType::Vertex, nzsl::ParseFromFile(shaderDir / "deferred_vert.nzsl")));
auto customMatSettings = std::make_shared<Nz::MaterialSettings>(std::move(customSettings)); Nz::MaterialPass customForwardPass;
customForwardPass.states.depthBuffer = true;
customForwardPass.shaders.emplace_back(std::make_shared<Nz::UberShader>(nzsl::ShaderStageType::Fragment, nzsl::ParseFromFile(shaderDir / "deferred_frag.nzsl")));
customForwardPass.shaders.emplace_back(std::make_shared<Nz::UberShader>(nzsl::ShaderStageType::Vertex, nzsl::ParseFromFile(shaderDir / "deferred_vert.nzsl")));
settings.AddPass("ForwardPass", customForwardPass);
std::shared_ptr<Nz::Material> spaceshipMat = std::make_shared<Nz::Material>(); Nz::MaterialPass customDepthPass = customForwardPass;
customDepthPass.options[Nz::CRC32("DepthPass")] = true;
settings.AddPass("DepthPass", customDepthPass);
std::shared_ptr<Nz::MaterialPass> spaceshipMatPass = std::make_shared<Nz::MaterialPass>(customMatSettings); auto deferredMaterial = std::make_shared<Nz::Material>(std::move(settings), "BasicMaterial");
spaceshipMatPass->EnableDepthBuffer(true);
std::shared_ptr<Nz::MaterialInstance> spaceshipMat = deferredMaterial->CreateInstance();
spaceshipMat->SetTextureProperty("AlphaMap", Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams));
spaceshipMat->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams));
std::shared_ptr<Nz::MaterialInstance> flareMaterial = deferredMaterial->CreateInstance();
flareMaterial->UpdatePassStates("ForwardPass", [](Nz::RenderStates& renderStates)
{ {
Nz::BasicMaterial basicMat(*spaceshipMatPass); renderStates.depthClamp = true;
basicMat.EnableAlphaTest(false); renderStates.depthWrite = false;
basicMat.SetAlphaMap(Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams)); renderStates.blending = true;
basicMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams)); renderStates.blend.modeColor = Nz::BlendEquation::Add;
} renderStates.blend.modeAlpha = Nz::BlendEquation::Add;
spaceshipMat->AddPass("ForwardPass", spaceshipMatPass); renderStates.blend.srcColor = Nz::BlendFunc::SrcAlpha;
renderStates.blend.dstColor = Nz::BlendFunc::InvSrcAlpha;
renderStates.blend.srcAlpha = Nz::BlendFunc::One;
renderStates.blend.dstAlpha = Nz::BlendFunc::One;
return true;
});
flareMaterial->UpdatePassFlags("ForwardPass", Nz::MaterialPassFlag::SortByDistance);
flareMaterial->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "flare1.png", texParams));
std::shared_ptr<Nz::Material> flareMaterial = std::make_shared<Nz::Material>(); Nz::TextureSamplerInfo planeSampler;
std::shared_ptr<Nz::MaterialPass> flareMaterialPass; planeSampler.anisotropyLevel = 16;
{ planeSampler.wrapModeU = Nz::SamplerWrap::Repeat;
flareMaterialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings()); planeSampler.wrapModeV = Nz::SamplerWrap::Repeat;
flareMaterialPass->EnableDepthBuffer(true);
flareMaterialPass->EnableDepthWrite(false);
flareMaterialPass->EnableDepthClamp(true);
flareMaterialPass->EnableFlag(Nz::MaterialPassFlag::SortByDistance); std::shared_ptr<Nz::MaterialInstance> planeMat = deferredMaterial->CreateInstance();
planeMat->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "dev_grey.png", texParams), planeSampler);
flareMaterialPass->EnableBlending(true);
flareMaterialPass->SetBlendEquation(Nz::BlendEquation::Add, Nz::BlendEquation::Add);
flareMaterialPass->SetBlendFunc(Nz::BlendFunc::SrcAlpha, Nz::BlendFunc::InvSrcAlpha, Nz::BlendFunc::One, Nz::BlendFunc::Zero);
Nz::BasicMaterial Osef(*flareMaterialPass);
Osef.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "flare1.png", texParams));
flareMaterial->AddPass("ForwardPass", flareMaterialPass);
}
std::shared_ptr<Nz::Material> planeMat = std::make_shared<Nz::Material>();
std::shared_ptr<Nz::MaterialPass> planeMatPass = std::make_shared<Nz::MaterialPass>(customMatSettings);
planeMatPass->EnableDepthBuffer(true);
{
Nz::BasicMaterial basicMat(*planeMatPass);
basicMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "dev_grey.png", texParams));
Nz::TextureSamplerInfo planeSampler;
planeSampler.anisotropyLevel = 16;
planeSampler.wrapModeU = Nz::SamplerWrap::Repeat;
planeSampler.wrapModeV = Nz::SamplerWrap::Repeat;
basicMat.SetBaseColorSampler(planeSampler);
}
planeMat->AddPass("ForwardPass", planeMatPass);
Nz::Model spaceshipModel(std::move(gfxMesh), spaceship->GetAABB()); Nz::Model spaceshipModel(std::move(gfxMesh), spaceship->GetAABB());
for (std::size_t i = 0; i < spaceshipModel.GetSubMeshCount(); ++i) for (std::size_t i = 0; i < spaceshipModel.GetSubMeshCount(); ++i)
@ -537,7 +526,7 @@ int main()
std::shared_ptr<Nz::ShaderBinding> godRaysShaderBinding = godraysPipelineInfo.pipelineLayout->AllocateShaderBinding(0); std::shared_ptr<Nz::ShaderBinding> godRaysShaderBinding = godraysPipelineInfo.pipelineLayout->AllocateShaderBinding(0);
/* /*
uniformExposure = 0.0034f; uniformExposure = 0.0034f;
uniformDecay = 1.0f; uniformDecay = 1.0f;
uniformDensity = 0.84f; uniformDensity = 0.84f;
uniformWeight = 5.65f; uniformWeight = 5.65f;
@ -588,7 +577,7 @@ int main()
meshPrimitiveParams.vertexDeclaration meshPrimitiveParams.vertexDeclaration
}); });
stencilPipelineInfo.colorWrite = false; stencilPipelineInfo.colorWriteMask = 0;
stencilPipelineInfo.depthBuffer = true; stencilPipelineInfo.depthBuffer = true;
stencilPipelineInfo.depthWrite = false; stencilPipelineInfo.depthWrite = false;
stencilPipelineInfo.faceCulling = false; stencilPipelineInfo.faceCulling = false;
@ -1466,15 +1455,15 @@ int main()
{ {
builder.PreTransferBarrier(); builder.PreTransferBarrier();
modelInstance1.UpdateBuffers(uploadPool, builder); modelInstance1.OnTransfer(frame, builder);
modelInstance2.UpdateBuffers(uploadPool, builder); modelInstance2.OnTransfer(frame, builder);
planeInstance.UpdateBuffers(uploadPool, builder); planeInstance.OnTransfer(frame, builder);
Nz::EulerAnglesf flareRotation(0.f, 0.f, elapsedTime * 10.f); Nz::EulerAnglesf flareRotation(0.f, 0.f, elapsedTime * 10.f);
flareInstance.UpdateWorldMatrix(Nz::Matrix4f::Transform(viewerPos + flarePosition, flareRotation)); flareInstance.UpdateWorldMatrix(Nz::Matrix4f::Transform(viewerPos + flarePosition, flareRotation));
flareInstance.UpdateBuffers(uploadPool, builder); flareInstance.OnTransfer(frame, builder);
viewerInstance.UpdateBuffers(uploadPool, builder); viewerInstance.OnTransfer(frame, builder);
// Update light buffer // Update light buffer
if (!spotLights.empty() && (lightUpdate || lightAnimation)) if (!spotLights.empty() && (lightUpdate || lightAnimation))
@ -1527,9 +1516,9 @@ int main()
builder.CopyBuffer(lightScatteringAllocation, godRaysUBO.get()); builder.CopyBuffer(lightScatteringAllocation, godRaysUBO.get());
} }
spaceshipMatPass->Update(frame, builder); spaceshipMat->OnTransfer(frame, builder);
planeMatPass->Update(frame, builder); planeMat->OnTransfer(frame, builder);
flareMaterialPass->Update(frame, builder); flareMaterial->OnTransfer(frame, builder);
builder.PostTransferBarrier(); builder.PostTransferBarrier();
} }

View File

@ -1,6 +1,8 @@
#include <Nazara/Core.hpp> #include <Nazara/Core.hpp>
#include <Nazara/Platform.hpp> #include <Nazara/Platform.hpp>
#include <Nazara/Graphics.hpp> #include <Nazara/Graphics.hpp>
#include <Nazara/Graphics/PropertyHandler/TexturePropertyHandler.hpp>
#include <Nazara/Graphics/PropertyHandler/UniformValuePropertyHandler.hpp>
#include <Nazara/Renderer.hpp> #include <Nazara/Renderer.hpp>
#include <Nazara/Utility.hpp> #include <Nazara/Utility.hpp>
#include <array> #include <array>
@ -19,7 +21,7 @@ int main()
if (std::getchar() == 'y') if (std::getchar() == 'y')
rendererConfig.preferredAPI = Nz::RenderAPI::Vulkan; rendererConfig.preferredAPI = Nz::RenderAPI::Vulkan;
else else
rendererConfig.preferredAPI = Nz::RenderAPI::OpenGL; rendererConfig.preferredAPI = Nz::RenderAPI::Vulkan;
Nz::Modules<Nz::Graphics> nazara(rendererConfig); Nz::Modules<Nz::Graphics> nazara(rendererConfig);
@ -61,30 +63,25 @@ int main()
texParams.renderDevice = device; texParams.renderDevice = device;
texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB; texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB;
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::Texture> diffuseTexture = Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams);
std::shared_ptr<Nz::MaterialPass> forwardPass = std::make_shared<Nz::MaterialPass>(Nz::PhongLightingMaterial::GetSettings()); std::shared_ptr<Nz::Material> material = Nz::Graphics::Instance()->GetDefaultMaterials().basicMaterial;
forwardPass->EnableDepthBuffer(true);
forwardPass->EnableFaceCulling(true);
material->AddPass("ForwardPass", forwardPass); std::shared_ptr<Nz::MaterialInstance> materialInstance = std::make_shared<Nz::MaterialInstance>(material);
materialInstance->SetTextureProperty(0, diffuseTexture);
materialInstance->SetValueProperty(0, Nz::Color::White);
std::shared_ptr<Nz::Texture> normalMap = Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/normal.png", texParams); std::shared_ptr<Nz::MaterialInstance> materialInstance2 = std::make_shared<Nz::MaterialInstance>(material);
materialInstance2->SetValueProperty(0, Nz::Color::Green);
Nz::PhongLightingMaterial phongMat(*forwardPass);
phongMat.EnableAlphaTest(false);
phongMat.SetAlphaMap(Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams));
phongMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams));
phongMat.SetNormalMap(Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/normal.png", texParams));
Nz::Model model(std::move(gfxMesh), spaceshipMesh->GetAABB()); Nz::Model model(std::move(gfxMesh), spaceshipMesh->GetAABB());
for (std::size_t i = 0; i < model.GetSubMeshCount(); ++i) for (std::size_t i = 0; i < model.GetSubMeshCount(); ++i)
model.SetMaterial(i, material); model.SetMaterial(i, materialInstance);
Nz::Vector2ui windowSize = window.GetSize(); Nz::Vector2ui windowSize = window.GetSize();
Nz::Camera camera(window.GetRenderTarget()); Nz::Camera camera(window.GetRenderTarget());
//camera.UpdateClearColor(Nz::Color::Gray); camera.UpdateClearColor(Nz::Color::Gray);
Nz::ViewerInstance& viewerInstance = camera.GetViewerInstance(); Nz::ViewerInstance& viewerInstance = camera.GetViewerInstance();
viewerInstance.UpdateTargetSize(Nz::Vector2f(window.GetSize())); viewerInstance.UpdateTargetSize(Nz::Vector2f(window.GetSize()));
@ -138,18 +135,18 @@ int main()
case Nz::WindowEventType::KeyPressed: case Nz::WindowEventType::KeyPressed:
if (event.key.virtualKey == Nz::Keyboard::VKey::A) if (event.key.virtualKey == Nz::Keyboard::VKey::A)
phongMat.EnableAlphaTest(!phongMat.IsAlphaTestEnabled());
else if (event.key.virtualKey == Nz::Keyboard::VKey::N)
{ {
if (phongMat.GetNormalMap()) for (std::size_t i = 0; i < model.GetSubMeshCount(); ++i)
phongMat.SetNormalMap({}); model.SetMaterial(i, materialInstance);
else }
phongMat.SetNormalMap(normalMap); else if (event.key.virtualKey == Nz::Keyboard::VKey::B)
{
for (std::size_t i = 0; i < model.GetSubMeshCount(); ++i)
model.SetMaterial(i, materialInstance2);
} }
else if (event.key.virtualKey == Nz::Keyboard::VKey::Space) else if (event.key.virtualKey == Nz::Keyboard::VKey::Space)
{ {
modelInstance->UpdateWorldMatrix(Nz::Matrix4f::Translate(viewerPos)); modelInstance->UpdateWorldMatrix(Nz::Matrix4f::Translate(viewerPos));
framePipeline.InvalidateWorldInstance(worldInstanceIndex1);
} }
break; break;
@ -227,8 +224,6 @@ int main()
viewerInstance.UpdateViewMatrix(Nz::Matrix4f::TransformInverse(viewerPos, camAngles)); viewerInstance.UpdateViewMatrix(Nz::Matrix4f::TransformInverse(viewerPos, camAngles));
viewerInstance.UpdateEyePosition(viewerPos); viewerInstance.UpdateEyePosition(viewerPos);
framePipeline.InvalidateViewer(cameraIndex);
framePipeline.Render(frame); framePipeline.Render(frame);
frame.Present(); frame.Present();

View File

@ -55,27 +55,22 @@ int main()
Nz::TextureParams srgbTexParams = texParams; Nz::TextureParams srgbTexParams = texParams;
srgbTexParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB; srgbTexParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB;
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>();
std::shared_ptr<Nz::MaterialPass> forwardPass = std::make_shared<Nz::MaterialPass>(Nz::PhysicallyBasedMaterial::GetSettings());
forwardPass->EnableDepthBuffer(true);
forwardPass->EnableFaceCulling(true);
material->AddPass("ForwardPass", forwardPass);
std::shared_ptr<Nz::Texture> normalMap = Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_normal.png", texParams); std::shared_ptr<Nz::Texture> normalMap = Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_normal.png", texParams);
Nz::PhysicallyBasedMaterial pbrMat(*forwardPass); std::shared_ptr<Nz::Material> material = Nz::Graphics::Instance()->GetDefaultMaterials().pbrMaterial;
pbrMat.EnableAlphaTest(false);
pbrMat.SetAlphaMap(Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams)); std::shared_ptr<Nz::MaterialInstance> materialInstance = std::make_shared<Nz::MaterialInstance>(material);
pbrMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_basecolor.png", srgbTexParams)); materialInstance->SetTextureProperty("AlphaMap", Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams));
pbrMat.SetMetallicMap(Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_metallic.png", texParams)); materialInstance->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_basecolor.png", texParams));
pbrMat.SetRoughnessMap(Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_roughness.png", texParams)); materialInstance->SetTextureProperty("MetallicMap", Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_metallic.png", texParams));
pbrMat.SetNormalMap(normalMap); materialInstance->SetTextureProperty("RoughnessMap", Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_roughness.png", texParams));
std::size_t normalMapProperty = materialInstance->FindTextureProperty("NormalMap");
materialInstance->SetTextureProperty(normalMapProperty, normalMap);
Nz::Model model(std::move(gfxMesh), sphereMesh->GetAABB()); Nz::Model model(std::move(gfxMesh), sphereMesh->GetAABB());
for (std::size_t i = 0; i < model.GetSubMeshCount(); ++i) for (std::size_t i = 0; i < model.GetSubMeshCount(); ++i)
model.SetMaterial(i, material); model.SetMaterial(i, materialInstance);
Nz::Vector2ui windowSize = window.GetSize(); Nz::Vector2ui windowSize = window.GetSize();
@ -129,10 +124,10 @@ int main()
case Nz::WindowEventType::KeyPressed: case Nz::WindowEventType::KeyPressed:
if (event.key.virtualKey == Nz::Keyboard::VKey::N) if (event.key.virtualKey == Nz::Keyboard::VKey::N)
{ {
if (pbrMat.GetNormalMap()) if (materialInstance->GetTextureProperty(normalMapProperty))
pbrMat.SetNormalMap({}); materialInstance->SetTextureProperty(normalMapProperty, {});
else else
pbrMat.SetNormalMap(normalMap); materialInstance->SetTextureProperty(normalMapProperty, normalMap);
} }
break; break;
@ -207,8 +202,6 @@ int main()
viewerInstance.UpdateViewMatrix(Nz::Matrix4f::TransformInverse(viewerPos, camAngles)); viewerInstance.UpdateViewMatrix(Nz::Matrix4f::TransformInverse(viewerPos, camAngles));
viewerInstance.UpdateEyePosition(viewerPos); viewerInstance.UpdateEyePosition(viewerPos);
framePipeline.InvalidateViewer(cameraIndex);
framePipeline.Render(frame); framePipeline.Render(frame);
frame.Present(); frame.Present();

View File

@ -52,7 +52,7 @@ int main()
Nz::Vector2ui windowSize = window.GetSize(); Nz::Vector2ui windowSize = window.GetSize();
physSytem.GetPhysWorld().SetGravity({ 0.f, -9.81f }); physSytem.GetPhysWorld().SetGravity({ 0.f, -98.1f });
entt::entity viewer = registry.create(); entt::entity viewer = registry.create();
{ {
@ -62,11 +62,6 @@ int main()
cameraComponent.UpdateClearColor(Nz::Color(0.5f, 0.5f, 0.5f)); cameraComponent.UpdateClearColor(Nz::Color(0.5f, 0.5f, 0.5f));
} }
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>();
std::shared_ptr<Nz::MaterialPass> materialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
material->AddPass("ForwardPass", materialPass);
Nz::TextureSamplerInfo samplerInfo; Nz::TextureSamplerInfo samplerInfo;
samplerInfo.anisotropyLevel = 8; samplerInfo.anisotropyLevel = 8;
@ -74,9 +69,8 @@ int main()
texParams.renderDevice = device; texParams.renderDevice = device;
texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB; texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB;
Nz::BasicMaterial basicMat(*materialPass); std::shared_ptr<Nz::MaterialInstance> material = Nz::Graphics::Instance()->GetDefaultMaterials().phongMaterial->CreateInstance();
basicMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams)); material->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams));
basicMat.SetBaseColorSampler(samplerInfo);
for (std::size_t y = 0; y < 10; ++y) for (std::size_t y = 0; y < 10; ++y)
{ {
@ -99,12 +93,7 @@ int main()
entt::entity groundEntity = registry.create(); entt::entity groundEntity = registry.create();
{ {
std::shared_ptr<Nz::Material> whiteMaterial = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::Sprite> sprite = std::make_shared<Nz::Sprite>(Nz::Graphics::Instance()->GetDefaultMaterials().basicDefault);
std::shared_ptr<Nz::MaterialPass> materialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
whiteMaterial->AddPass("ForwardPass", materialPass);
std::shared_ptr<Nz::Sprite> sprite = std::make_shared<Nz::Sprite>(whiteMaterial);
sprite->SetSize({ 800.f, 20.f }); sprite->SetSize({ 800.f, 20.f });
sprite->SetOrigin({ 400.f, 10.f, 0.f }); sprite->SetOrigin({ 400.f, 10.f, 0.f });
@ -158,13 +147,6 @@ int main()
} }
} }
if (updateClock.GetMilliseconds() > 1000 / 60)
{
float updateTime = updateClock.Restart() / 1'000'000.f;
physSytem.Update(1000.f / 60.f);
}
systemGraph.Update(); systemGraph.Update();
fps++; fps++;

View File

@ -56,22 +56,6 @@ int main()
const Nz::Boxf& spaceshipAABB = spaceshipMesh->GetAABB(); const Nz::Boxf& spaceshipAABB = spaceshipMesh->GetAABB();
std::shared_ptr<Nz::GraphicalMesh> gfxMesh = Nz::GraphicalMesh::BuildFromMesh(*spaceshipMesh); std::shared_ptr<Nz::GraphicalMesh> gfxMesh = Nz::GraphicalMesh::BuildFromMesh(*spaceshipMesh);
// Texture
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>();
std::shared_ptr<Nz::MaterialPass> depthPass = std::make_shared<Nz::MaterialPass>(Nz::DepthMaterial::GetSettings());
depthPass->EnableDepthBuffer(true);
depthPass->EnableDepthClamp(true);
depthPass->EnableFaceCulling(true);
std::shared_ptr<Nz::MaterialPass> materialPass = std::make_shared<Nz::MaterialPass>(Nz::PhongLightingMaterial::GetSettings());
materialPass->EnableDepthBuffer(true);
materialPass->EnableDepthClamp(true);
materialPass->EnableFaceCulling(true);
material->AddPass("DepthPass", depthPass);
material->AddPass("ForwardPass", materialPass);
Nz::TextureSamplerInfo samplerInfo; Nz::TextureSamplerInfo samplerInfo;
samplerInfo.anisotropyLevel = 8; samplerInfo.anisotropyLevel = 8;
@ -79,35 +63,15 @@ int main()
texParams.renderDevice = device; texParams.renderDevice = device;
texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB; texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB;
Nz::BasicMaterial basicMat(*materialPass); std::shared_ptr<Nz::MaterialInstance> material = Nz::Graphics::Instance()->GetDefaultMaterials().phongMaterial->CreateInstance();
basicMat.EnableAlphaTest(false); material->SetTextureProperty("AlphaMap", Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams));
basicMat.SetAlphaMap(Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams)); material->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams));
basicMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams));
basicMat.SetBaseColorSampler(samplerInfo);
Nz::DepthMaterial basicMatDepth(*depthPass);
basicMatDepth.SetAlphaMap(Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams));
std::shared_ptr<Nz::Model> model = std::make_shared<Nz::Model>(std::move(gfxMesh), spaceshipAABB); std::shared_ptr<Nz::Model> model = std::make_shared<Nz::Model>(std::move(gfxMesh), spaceshipAABB);
for (std::size_t i = 0; i < model->GetSubMeshCount(); ++i) for (std::size_t i = 0; i < model->GetSubMeshCount(); ++i)
model->SetMaterial(i, material); model->SetMaterial(i, material);
std::shared_ptr<Nz::Material> spriteMaterial = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::TextSprite> sprite = std::make_shared<Nz::TextSprite>();
std::shared_ptr<Nz::MaterialPass> spriteMaterialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
spriteMaterialPass->EnableDepthBuffer(true);
spriteMaterialPass->EnableDepthWrite(false);
spriteMaterialPass->EnableDepthClamp(true);
spriteMaterialPass->EnableFlag(Nz::MaterialPassFlag::SortByDistance);
spriteMaterialPass->EnableBlending(true);
spriteMaterialPass->SetBlendEquation(Nz::BlendEquation::Add, Nz::BlendEquation::Add);
spriteMaterialPass->SetBlendFunc(Nz::BlendFunc::SrcAlpha, Nz::BlendFunc::InvSrcAlpha, Nz::BlendFunc::One, Nz::BlendFunc::Zero);
spriteMaterial->AddPass("ForwardPass", spriteMaterialPass);
std::shared_ptr<Nz::TextSprite> sprite = std::make_shared<Nz::TextSprite>(spriteMaterial);
sprite->Update(Nz::SimpleTextDrawer::Draw("Voix ambiguë d'un cœur qui, au zéphyr, préfère les jattes de kiwis", 72), 0.01f); sprite->Update(Nz::SimpleTextDrawer::Draw("Voix ambiguë d'un cœur qui, au zéphyr, préfère les jattes de kiwis", 72), 0.01f);
Nz::VertexMapper vertexMapper(*spaceshipMesh->GetSubMesh(0)); Nz::VertexMapper vertexMapper(*spaceshipMesh->GetSubMesh(0));
@ -134,16 +98,16 @@ int main()
auto shipCollider = std::make_shared<Nz::ConvexCollider3D>(vertices, vertexMapper.GetVertexCount(), 0.01f); auto shipCollider = std::make_shared<Nz::ConvexCollider3D>(vertices, vertexMapper.GetVertexCount(), 0.01f);
std::shared_ptr<Nz::Material> colliderMat = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::MaterialInstance> colliderMat = Nz::Graphics::Instance()->GetDefaultMaterials().basicMaterial->CreateInstance();
colliderMat->SetValueProperty("BaseColor", Nz::Color::Green);
std::shared_ptr<Nz::MaterialPass> colliderMatPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings()); for (std::string_view passName : { "DepthPass", "ForwardPass" })
colliderMatPass->EnableDepthBuffer(true); {
colliderMatPass->SetPrimitiveMode(Nz::PrimitiveMode::LineList); colliderMat->UpdatePassStates(passName, [](Nz::RenderStates& states)
{
colliderMat->AddPass("ForwardPass", colliderMatPass); states.primitiveMode = Nz::PrimitiveMode::LineList;
return true;
Nz::BasicMaterial colliderBasicMat(*colliderMatPass); });
colliderBasicMat.SetBaseColor(Nz::Color::Green); }
std::shared_ptr<Nz::Model> colliderModel; std::shared_ptr<Nz::Model> colliderModel;
{ {
@ -245,9 +209,8 @@ int main()
case Nz::WindowEventType::KeyPressed: case Nz::WindowEventType::KeyPressed:
if (event.key.virtualKey == Nz::Keyboard::VKey::A) if (event.key.virtualKey == Nz::Keyboard::VKey::A)
{ {
//canvas2D.Resize({ 1920.f, 1080.f }); bool alphaTestEnabled = std::get<bool>(*material->GetValueProperty("AlphaTest"));
basicMat.EnableAlphaTest(!basicMat.IsAlphaTestEnabled()); material->SetValueProperty("AlphaTest", !alphaTestEnabled);
basicMatDepth.EnableAlphaTest(!basicMatDepth.IsAlphaTestEnabled());
} }
else if (event.key.virtualKey == Nz::Keyboard::VKey::B) else if (event.key.virtualKey == Nz::Keyboard::VKey::B)
{ {

View File

@ -111,13 +111,18 @@ int main()
const Nz::Boxf& bobAABB = bobMesh->GetAABB(); const Nz::Boxf& bobAABB = bobMesh->GetAABB();
std::shared_ptr<Nz::GraphicalMesh> bobGfxMesh = Nz::GraphicalMesh::BuildFromMesh(*bobMesh); std::shared_ptr<Nz::GraphicalMesh> bobGfxMesh = Nz::GraphicalMesh::BuildFromMesh(*bobMesh);
std::shared_ptr<Nz::Material> material = Nz::Graphics::Instance()->GetDefaultMaterials().basicMaterial;
std::shared_ptr<Nz::Model> bobModel = std::make_shared<Nz::Model>(std::move(bobGfxMesh), bobAABB); std::shared_ptr<Nz::Model> bobModel = std::make_shared<Nz::Model>(std::move(bobGfxMesh), bobAABB);
std::vector<std::shared_ptr<Nz::Material>> materials(bobMesh->GetMaterialCount()); std::vector<std::shared_ptr<Nz::MaterialInstance>> materials(bobMesh->GetMaterialCount());
for (std::size_t i = 0; i < bobMesh->GetMaterialCount(); ++i) for (std::size_t i = 0; i < bobMesh->GetMaterialCount(); ++i)
{ {
materials[i] = std::make_shared<Nz::MaterialInstance>(material);
std::string matPath = bobMesh->GetMaterialData(i).GetStringParameter(Nz::MaterialData::BaseColorTexturePath).GetValueOr(""); std::string matPath = bobMesh->GetMaterialData(i).GetStringParameter(Nz::MaterialData::BaseColorTexturePath).GetValueOr("");
if (!matPath.empty()) if (!matPath.empty())
materials[i] = Nz::Material::LoadFromFile(matPath); materials[i]->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(matPath, texParams));
} }
for (std::size_t i = 0; i < bobMesh->GetSubMeshCount(); ++i) for (std::size_t i = 0; i < bobMesh->GetSubMeshCount(); ++i)
@ -148,7 +153,7 @@ int main()
auto& bobNode = bobEntity.emplace<Nz::NodeComponent>(); auto& bobNode = bobEntity.emplace<Nz::NodeComponent>();
//bobNode.SetRotation(Nz::EulerAnglesf(-90.f, -90.f, 0.f)); //bobNode.SetRotation(Nz::EulerAnglesf(-90.f, -90.f, 0.f));
//bobNode.SetScale(1.f / 40.f * 0.5f); //bobNode.SetScale(1.f / 40.f * 0.5f);
//bobNode.SetPosition(bobNode.GetScale() * Nz::Vector3f(0.f, -bobAABB.height / 2.f + bobAABB.y, 0.f)); //bobNode.SetPosition(Nz::Vector3f(0.f, -1.f, 0.f));
auto& bobGfx = bobEntity.emplace<Nz::GraphicsComponent>(); auto& bobGfx = bobEntity.emplace<Nz::GraphicsComponent>();
bobGfx.AttachRenderable(bobModel, 0xFFFFFFFF); bobGfx.AttachRenderable(bobModel, 0xFFFFFFFF);
@ -173,24 +178,12 @@ int main()
Nz::TextureParams srgbTexParams = texParams; Nz::TextureParams srgbTexParams = texParams;
srgbTexParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB; srgbTexParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB;
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::MaterialInstance> sphereMat = std::make_shared<Nz::MaterialInstance>(material);
sphereMat->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_basecolor.png", srgbTexParams));
std::shared_ptr<Nz::MaterialPass> forwardPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
forwardPass->EnableDepthBuffer(true);
forwardPass->EnableFaceCulling(true);
material->AddPass("ForwardPass", forwardPass);
std::shared_ptr<Nz::Texture> normalMap = Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_normal.png", texParams);
Nz::BasicMaterial pbrMat(*forwardPass);
pbrMat.EnableAlphaTest(false);
pbrMat.SetAlphaMap(Nz::Texture::LoadFromFile(resourceDir / "alphatile.png", texParams));
pbrMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Rusty/rustediron2_basecolor.png", srgbTexParams));
std::shared_ptr<Nz::Model> sphereModel = std::make_shared<Nz::Model>(std::move(gfxMesh), sphereMesh->GetAABB()); std::shared_ptr<Nz::Model> sphereModel = std::make_shared<Nz::Model>(std::move(gfxMesh), sphereMesh->GetAABB());
for (std::size_t i = 0; i < sphereModel->GetSubMeshCount(); ++i) for (std::size_t i = 0; i < sphereModel->GetSubMeshCount(); ++i)
sphereModel->SetMaterial(i, material); sphereModel->SetMaterial(i, sphereMat);
auto& sphereNode = registry.emplace<Nz::NodeComponent>(sphereEntity); auto& sphereNode = registry.emplace<Nz::NodeComponent>(sphereEntity);
sphereNode.SetScale(0.1f); sphereNode.SetScale(0.1f);
@ -229,32 +222,24 @@ int main()
std::shared_ptr<Nz::GraphicalMesh> planeMeshGfx = Nz::GraphicalMesh::BuildFromMesh(planeMesh); std::shared_ptr<Nz::GraphicalMesh> planeMeshGfx = Nz::GraphicalMesh::BuildFromMesh(planeMesh);
std::shared_ptr<Nz::Material> planeMat = std::make_shared<Nz::Material>(); Nz::TextureSamplerInfo planeSampler;
planeSampler.anisotropyLevel = 16;
planeSampler.wrapModeU = Nz::SamplerWrap::Repeat;
planeSampler.wrapModeV = Nz::SamplerWrap::Repeat;
std::shared_ptr<Nz::MaterialPass> planeMatPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings()); std::shared_ptr<Nz::MaterialInstance> planeMat = std::make_shared<Nz::MaterialInstance>(material);
planeMatPass->EnableDepthBuffer(true); planeMat->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "dev_grey.png", texParams), planeSampler);
{
Nz::BasicMaterial basicMat(*planeMatPass);
basicMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "dev_grey.png", texParams));
Nz::TextureSamplerInfo planeSampler;
planeSampler.anisotropyLevel = 16;
planeSampler.wrapModeU = Nz::SamplerWrap::Repeat;
planeSampler.wrapModeV = Nz::SamplerWrap::Repeat;
basicMat.SetBaseColorSampler(planeSampler);
}
planeMat->AddPass("ForwardPass", planeMatPass);
std::shared_ptr<Nz::Model> planeModel = std::make_shared<Nz::Model>(std::move(planeMeshGfx), planeMesh.GetAABB()); std::shared_ptr<Nz::Model> planeModel = std::make_shared<Nz::Model>(std::move(planeMeshGfx), planeMesh.GetAABB());
planeModel->SetMaterial(0, planeMat); planeModel->SetMaterial(0, planeMat);
auto& planeGfx = registry.emplace<Nz::GraphicsComponent>(planeEntity);
planeGfx.AttachRenderable(planeModel, 0xFFFFFFFF);
auto& planeNode = registry.emplace<Nz::NodeComponent>(planeEntity); auto& planeNode = registry.emplace<Nz::NodeComponent>(planeEntity);
auto& planeBody = registry.emplace<Nz::RigidBody3DComponent>(planeEntity, &physSytem.GetPhysWorld()); auto& planeBody = registry.emplace<Nz::RigidBody3DComponent>(planeEntity, &physSytem.GetPhysWorld());
planeBody.SetGeom(std::make_shared<Nz::BoxCollider3D>(Nz::Vector3f(planeSize.x, 0.5f, planeSize.y), Nz::Vector3f(0.f, -0.25f, 0.f))); planeBody.SetGeom(std::make_shared<Nz::BoxCollider3D>(Nz::Vector3f(planeSize.x, 0.5f, planeSize.y), Nz::Vector3f(0.f, -0.25f, 0.f)));
auto& planeGfx = registry.emplace<Nz::GraphicsComponent>(planeEntity);
planeGfx.AttachRenderable(planeModel, 0xFFFFFFFF);
} }
window.EnableEventPolling(true); window.EnableEventPolling(true);
@ -266,6 +251,8 @@ int main()
Nz::EulerAnglesf camAngles = Nz::EulerAnglesf(-30.f, 0.f, 0.f); Nz::EulerAnglesf camAngles = Nz::EulerAnglesf(-30.f, 0.f, 0.f);
Nz::UInt64 lastTime = Nz::GetElapsedMicroseconds(); Nz::UInt64 lastTime = Nz::GetElapsedMicroseconds();
Nz::UInt64 fps = 0; Nz::UInt64 fps = 0;
bool paused = false;
while (window.IsOpen()) while (window.IsOpen())
{ {
Nz::UInt64 now = Nz::GetElapsedMicroseconds(); Nz::UInt64 now = Nz::GetElapsedMicroseconds();
@ -282,7 +269,12 @@ int main()
break; break;
case Nz::WindowEventType::KeyPressed: case Nz::WindowEventType::KeyPressed:
{
if (event.type == Nz::WindowEventType::KeyPressed && event.key.virtualKey == Nz::Keyboard::VKey::P)
paused = !paused;
break; break;
}
case Nz::WindowEventType::MouseMoved: case Nz::WindowEventType::MouseMoved:
{ {
@ -329,20 +321,23 @@ int main()
if (Nz::Keyboard::IsKeyPressed(Nz::Keyboard::VKey::Right) || Nz::Keyboard::IsKeyPressed(Nz::Keyboard::VKey::D)) if (Nz::Keyboard::IsKeyPressed(Nz::Keyboard::VKey::Right) || Nz::Keyboard::IsKeyPressed(Nz::Keyboard::VKey::D))
playerBody.AddForce(Nz::Vector3f::Right() * 25.f * mass, Nz::CoordSys::Local); playerBody.AddForce(Nz::Vector3f::Right() * 25.f * mass, Nz::CoordSys::Local);
incr += updateTime * bobAnim->GetSequence(0)->frameRate * 1.5f; if (!paused)
while (incr >= 1.f)
{ {
incr -= 1.f; incr += updateTime * bobAnim->GetSequence(0)->frameRate * 1.5f;
while (incr >= 1.f)
{
incr -= 1.f;
currentFrame = nextFrame; currentFrame = nextFrame;
nextFrame++; nextFrame++;
if (nextFrame >= bobAnim->GetFrameCount()) if (nextFrame >= bobAnim->GetFrameCount())
nextFrame = 0; nextFrame = 0;
}
std::cout << currentFrame << std::endl;
bobAnim->AnimateSkeleton(skeleton.get(), currentFrame, nextFrame, incr);
} }
std::cout << currentFrame << std::endl;
bobAnim->AnimateSkeleton(skeleton.get(), currentFrame, nextFrame, incr);
//for (std::size_t i = 0; i < skeleton.GetJointCount(); ++i) //for (std::size_t i = 0; i < skeleton.GetJointCount(); ++i)
// matrices[i] = skeleton.GetJoint(i)->GetSkinningMatrix(); // matrices[i] = skeleton.GetJoint(i)->GetSkinningMatrix();

View File

@ -33,20 +33,7 @@ int main()
textDrawer.SetOutlineThickness(4.f); textDrawer.SetOutlineThickness(4.f);
textDrawer.SetText("Hello world !"); textDrawer.SetText("Hello world !");
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::TextSprite> textSprite = std::make_shared<Nz::TextSprite>();
std::shared_ptr<Nz::MaterialPass> materialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
materialPass->EnableDepthBuffer(true);
materialPass->EnableDepthWrite(false);
materialPass->EnableScissorTest(true);
materialPass->EnableBlending(true);
materialPass->SetBlendEquation(Nz::BlendEquation::Add, Nz::BlendEquation::Add);
materialPass->SetBlendFunc(Nz::BlendFunc::SrcAlpha, Nz::BlendFunc::InvSrcAlpha, Nz::BlendFunc::One, Nz::BlendFunc::One);
material = std::make_shared<Nz::Material>();
material->AddPass("ForwardPass", materialPass);
std::shared_ptr<Nz::TextSprite> textSprite = std::make_shared<Nz::TextSprite>(material);
textSprite->Update(textDrawer); textSprite->Update(textDrawer);
entt::entity textEntity = registry.create(); entt::entity textEntity = registry.create();

View File

@ -33,20 +33,7 @@ int main()
textDrawer.SetOutlineThickness(4.f); textDrawer.SetOutlineThickness(4.f);
textDrawer.SetText("Press a key"); textDrawer.SetText("Press a key");
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::TextSprite> textSprite = std::make_shared<Nz::TextSprite>();
std::shared_ptr<Nz::MaterialPass> materialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
materialPass->EnableDepthBuffer(true);
materialPass->EnableDepthWrite(false);
materialPass->EnableScissorTest(true);
materialPass->EnableBlending(true);
materialPass->SetBlendEquation(Nz::BlendEquation::Add, Nz::BlendEquation::Add);
materialPass->SetBlendFunc(Nz::BlendFunc::SrcAlpha, Nz::BlendFunc::InvSrcAlpha, Nz::BlendFunc::One, Nz::BlendFunc::One);
material = std::make_shared<Nz::Material>();
material->AddPass("ForwardPass", materialPass);
std::shared_ptr<Nz::TextSprite> textSprite = std::make_shared<Nz::TextSprite>(material);
textSprite->Update(textDrawer); textSprite->Update(textDrawer);
entt::entity textEntity = registry.create(); entt::entity textEntity = registry.create();

View File

@ -66,10 +66,7 @@ int main()
labelWidget->UpdateText(Nz::SimpleTextDrawer::Draw("You clicked the button " + std::to_string(++clickCount) + " times", 72)); labelWidget->UpdateText(Nz::SimpleTextDrawer::Draw("You clicked the button " + std::to_string(++clickCount) + " times", 72));
}); });
std::shared_ptr<Nz::Material> material = std::make_shared<Nz::Material>(); std::shared_ptr<Nz::Material> material = Nz::Graphics::Instance()->GetDefaultMaterials().basicMaterial;
std::shared_ptr<Nz::MaterialPass> materialPass = std::make_shared<Nz::MaterialPass>(Nz::BasicMaterial::GetSettings());
material->AddPass("ForwardPass", materialPass);
Nz::TextureSamplerInfo samplerInfo; Nz::TextureSamplerInfo samplerInfo;
samplerInfo.anisotropyLevel = 8; samplerInfo.anisotropyLevel = 8;
@ -78,15 +75,14 @@ int main()
texParams.renderDevice = device; texParams.renderDevice = device;
texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB; texParams.loadFormat = Nz::PixelFormat::RGBA8_SRGB;
Nz::BasicMaterial basicMat(*materialPass); std::shared_ptr<Nz::MaterialInstance> materialInstance = material->CreateInstance();
basicMat.SetBaseColorMap(Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams)); materialInstance->SetTextureProperty("BaseColorMap", Nz::Texture::LoadFromFile(resourceDir / "Spaceship/Texture/diffuse.png", texParams));
basicMat.SetBaseColorSampler(samplerInfo);
Nz::ImageWidget* imageWidget = canvas2D.Add<Nz::ImageWidget>(material); Nz::ImageWidget* imageWidget = canvas2D.Add<Nz::ImageWidget>(materialInstance);
imageWidget->SetPosition(1200.f, 200.f); imageWidget->SetPosition(1200.f, 200.f);
imageWidget->Resize(imageWidget->GetPreferredSize() / 4.f); imageWidget->Resize(imageWidget->GetPreferredSize() / 4.f);
Nz::ImageButtonWidget* imageButtonWidget = canvas2D.Add<Nz::ImageButtonWidget>(material); Nz::ImageButtonWidget* imageButtonWidget = canvas2D.Add<Nz::ImageButtonWidget>(materialInstance);
imageButtonWidget->SetPosition(1400, 500.f); imageButtonWidget->SetPosition(1400, 500.f);
imageButtonWidget->Resize(imageButtonWidget->GetPreferredSize() / 4.f); imageButtonWidget->Resize(imageButtonWidget->GetPreferredSize() / 4.f);

View File

@ -13,7 +13,7 @@ namespace Nz
inline bool EndsWith(const std::string_view& str, const std::string_view& s) inline bool EndsWith(const std::string_view& str, const std::string_view& s)
{ {
//FIXME: Replace with proper C++20 value once it's available //FIXME: Replace with proper C++20 value once it's available
#if __cplusplus > 201703L #if NAZARA_CPP_VER > 201703L
// C++20 // C++20
return str.ends_with(s); return str.ends_with(s);
#else #else
@ -53,7 +53,7 @@ namespace Nz
inline bool StartsWith(const std::string_view& str, const std::string_view& s) inline bool StartsWith(const std::string_view& str, const std::string_view& s)
{ {
//FIXME: Replace with proper C++20 value once it's available //FIXME: Replace with proper C++20 value once it's available
#if __cplusplus > 201703L #if NAZARA_CPP_VER > 201703L
// C++20 // C++20
return str.starts_with(s); return str.starts_with(s);
#else #else

View File

@ -32,11 +32,9 @@
#include <Nazara/Graphics/AbstractViewer.hpp> #include <Nazara/Graphics/AbstractViewer.hpp>
#include <Nazara/Graphics/Algorithm.hpp> #include <Nazara/Graphics/Algorithm.hpp>
#include <Nazara/Graphics/BakedFrameGraph.hpp> #include <Nazara/Graphics/BakedFrameGraph.hpp>
#include <Nazara/Graphics/BasicMaterial.hpp>
#include <Nazara/Graphics/Camera.hpp> #include <Nazara/Graphics/Camera.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/DebugDrawPipelinePass.hpp> #include <Nazara/Graphics/DebugDrawPipelinePass.hpp>
#include <Nazara/Graphics/DepthMaterial.hpp>
#include <Nazara/Graphics/DepthPipelinePass.hpp> #include <Nazara/Graphics/DepthPipelinePass.hpp>
#include <Nazara/Graphics/DirectionalLight.hpp> #include <Nazara/Graphics/DirectionalLight.hpp>
#include <Nazara/Graphics/ElementRenderer.hpp> #include <Nazara/Graphics/ElementRenderer.hpp>
@ -56,15 +54,16 @@
#include <Nazara/Graphics/Light.hpp> #include <Nazara/Graphics/Light.hpp>
#include <Nazara/Graphics/LinearSlicedSprite.hpp> #include <Nazara/Graphics/LinearSlicedSprite.hpp>
#include <Nazara/Graphics/Material.hpp> #include <Nazara/Graphics/Material.hpp>
#include <Nazara/Graphics/MaterialInstance.hpp>
#include <Nazara/Graphics/MaterialPass.hpp> #include <Nazara/Graphics/MaterialPass.hpp>
#include <Nazara/Graphics/MaterialPassRegistry.hpp> #include <Nazara/Graphics/MaterialPassRegistry.hpp>
#include <Nazara/Graphics/MaterialPipeline.hpp> #include <Nazara/Graphics/MaterialPipeline.hpp>
#include <Nazara/Graphics/MaterialSettings.hpp> #include <Nazara/Graphics/MaterialSettings.hpp>
#include <Nazara/Graphics/Model.hpp> #include <Nazara/Graphics/Model.hpp>
#include <Nazara/Graphics/PhongLightingMaterial.hpp>
#include <Nazara/Graphics/PhysicallyBasedMaterial.hpp>
#include <Nazara/Graphics/PointLight.hpp> #include <Nazara/Graphics/PointLight.hpp>
#include <Nazara/Graphics/PredefinedMaterials.hpp>
#include <Nazara/Graphics/PredefinedShaderStructs.hpp> #include <Nazara/Graphics/PredefinedShaderStructs.hpp>
#include <Nazara/Graphics/RenderBufferPool.hpp>
#include <Nazara/Graphics/RenderElement.hpp> #include <Nazara/Graphics/RenderElement.hpp>
#include <Nazara/Graphics/RenderElementOwner.hpp> #include <Nazara/Graphics/RenderElementOwner.hpp>
#include <Nazara/Graphics/RenderElementPool.hpp> #include <Nazara/Graphics/RenderElementPool.hpp>
@ -72,6 +71,7 @@
#include <Nazara/Graphics/RenderQueueRegistry.hpp> #include <Nazara/Graphics/RenderQueueRegistry.hpp>
#include <Nazara/Graphics/RenderSpriteChain.hpp> #include <Nazara/Graphics/RenderSpriteChain.hpp>
#include <Nazara/Graphics/RenderSubmesh.hpp> #include <Nazara/Graphics/RenderSubmesh.hpp>
#include <Nazara/Graphics/ShaderReflection.hpp>
#include <Nazara/Graphics/SkeletonInstance.hpp> #include <Nazara/Graphics/SkeletonInstance.hpp>
#include <Nazara/Graphics/SlicedSprite.hpp> #include <Nazara/Graphics/SlicedSprite.hpp>
#include <Nazara/Graphics/SpotLight.hpp> #include <Nazara/Graphics/SpotLight.hpp>
@ -80,6 +80,7 @@
#include <Nazara/Graphics/SubmeshRenderer.hpp> #include <Nazara/Graphics/SubmeshRenderer.hpp>
#include <Nazara/Graphics/TextSprite.hpp> #include <Nazara/Graphics/TextSprite.hpp>
#include <Nazara/Graphics/TextureSamplerCache.hpp> #include <Nazara/Graphics/TextureSamplerCache.hpp>
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Graphics/UberShader.hpp> #include <Nazara/Graphics/UberShader.hpp>
#include <Nazara/Graphics/ViewerInstance.hpp> #include <Nazara/Graphics/ViewerInstance.hpp>
#include <Nazara/Graphics/WorldInstance.hpp> #include <Nazara/Graphics/WorldInstance.hpp>

View File

@ -1,123 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_BASICMATERIAL_HPP
#define NAZARA_GRAPHICS_BASICMATERIAL_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/MaterialPass.hpp>
namespace nzsl
{
class FieldOffsets;
}
namespace Nz
{
class NAZARA_GRAPHICS_API BasicMaterial
{
friend class MaterialPipeline;
public:
struct BasicUniformOffsets;
BasicMaterial(MaterialPass& material);
~BasicMaterial() = default;
inline void EnableAlphaTest(bool alphaTest);
inline const std::shared_ptr<Texture>& GetAlphaMap() const;
inline const TextureSamplerInfo& GetAlphaSampler() const;
float GetAlphaTestThreshold() const;
Color GetBaseColor() const;
inline const std::shared_ptr<Texture>& GetBaseColorMap() const;
inline const TextureSamplerInfo& GetBaseColorSampler() const;
inline bool IsAlphaTestEnabled() const;
inline bool HasAlphaMap() const;
inline bool HasAlphaTest() const;
inline bool HasAlphaTestThreshold() const;
inline bool HasBaseColor() const;
inline bool HasBaseColorMap() const;
inline void SetAlphaMap(std::shared_ptr<Texture> alphaMap);
inline void SetAlphaSampler(TextureSamplerInfo alphaSampler);
void SetAlphaTestThreshold(float alphaThreshold);
void SetBaseColor(const Color& baseColor);
inline void SetBaseColorMap(std::shared_ptr<Texture> baseColorMap);
inline void SetBaseColorSampler(TextureSamplerInfo baseColorSampler);
static inline const BasicUniformOffsets& GetOffsets();
static inline const std::shared_ptr<MaterialSettings>& GetSettings();
struct BasicUniformOffsets
{
std::size_t alphaThreshold;
std::size_t baseColor;
std::size_t totalSize;
};
protected:
struct NoInit {};
inline BasicMaterial(MaterialPass& material, NoInit);
struct BasicOptionIndexes
{
std::size_t alphaTest;
std::size_t hasAlphaMap;
std::size_t hasBaseColorMap;
};
struct BasicTextureIndexes
{
std::size_t alpha;
std::size_t baseColor;
};
struct BasicBuildOptions
{
// Common
std::vector<UInt8> defaultValues;
std::size_t* uniformBlockIndex = nullptr;
std::vector<std::shared_ptr<UberShader>> shaders;
// Basic
BasicUniformOffsets basicOffsets;
BasicOptionIndexes* basicOptionIndexes = nullptr;
BasicTextureIndexes* basicTextureIndexes = nullptr;
};
inline MaterialPass& GetMaterial();
inline const MaterialPass& GetMaterial() const;
static MaterialSettings::Builder Build(BasicBuildOptions& options);
static std::vector<std::shared_ptr<UberShader>> BuildShaders();
static std::pair<BasicUniformOffsets, nzsl::FieldOffsets> BuildUniformOffsets();
std::size_t m_uniformBlockIndex;
BasicOptionIndexes m_basicOptionIndexes;
BasicTextureIndexes m_basicTextureIndexes;
BasicUniformOffsets m_basicUniformOffsets;
static std::shared_ptr<MaterialSettings> s_basicMaterialSettings;
static std::size_t s_uniformBlockIndex;
static BasicOptionIndexes s_basicOptionIndexes;
static BasicTextureIndexes s_basicTextureIndexes;
static BasicUniformOffsets s_basicUniformOffsets;
private:
static bool Initialize();
static void Uninitialize();
MaterialPass& m_material;
};
}
#include <Nazara/Graphics/BasicMaterial.inl>
#endif // NAZARA_GRAPHICS_BASICMATERIAL_HPP

View File

@ -1,149 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/BasicMaterial.hpp>
#include <Nazara/Core/ErrorFlags.hpp>
#include <memory>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline BasicMaterial::BasicMaterial(MaterialPass& material, NoInit) :
m_material(material)
{
}
/*!
* \brief Enable/Disable alpha test for this material
*
* When enabled, all objects using this material will be rendered using alpha testing,
* rejecting pixels if their alpha component is under a defined threshold.
* This allows some kind of transparency with a much cheaper cost as it doesn't prevent any optimization (as deferred rendering or batching).
*
* \param alphaTest Defines if this material will use alpha testing
*
* \remark Invalidates the pipeline
*
* \see IsAlphaTestEnabled
* \see SetAlphaThreshold
*/
inline void BasicMaterial::EnableAlphaTest(bool alphaTest)
{
NazaraAssert(HasAlphaTest(), "Material has no alpha test option");
m_material.SetOptionValue(m_basicOptionIndexes.alphaTest, alphaTest);
}
inline const std::shared_ptr<Texture>& BasicMaterial::GetAlphaMap() const
{
NazaraAssert(HasAlphaMap(), "Material has no alpha texture slot");
return m_material.GetTexture(m_basicTextureIndexes.alpha);
}
inline const TextureSamplerInfo& BasicMaterial::GetAlphaSampler() const
{
NazaraAssert(HasAlphaMap(), "Material has no alpha texture slot");
return m_material.GetTextureSampler(m_basicTextureIndexes.alpha);
}
inline const std::shared_ptr<Texture>& BasicMaterial::GetBaseColorMap() const
{
NazaraAssert(HasBaseColorMap(), "Material has no alpha texture slot");
return m_material.GetTexture(m_basicTextureIndexes.baseColor);
}
inline const TextureSamplerInfo& BasicMaterial::GetBaseColorSampler() const
{
NazaraAssert(HasBaseColorMap(), "Material has no alpha texture slot");
return m_material.GetTextureSampler(m_basicTextureIndexes.baseColor);
}
inline bool BasicMaterial::IsAlphaTestEnabled() const
{
NazaraAssert(HasAlphaTest(), "Material has no alpha test option");
const auto& optionOpt = m_material.GetOptionValue(m_basicOptionIndexes.alphaTest);
if (std::holds_alternative<nzsl::Ast::NoValue>(optionOpt))
return false;
return std::get<bool>(optionOpt);
}
inline bool BasicMaterial::HasAlphaMap() const
{
return m_basicTextureIndexes.alpha != MaterialSettings::InvalidIndex;
}
inline bool BasicMaterial::HasAlphaTest() const
{
return m_basicOptionIndexes.alphaTest != MaterialSettings::InvalidIndex;
}
inline bool BasicMaterial::HasAlphaTestThreshold() const
{
return m_basicUniformOffsets.alphaThreshold != MaterialSettings::InvalidIndex;
}
inline bool BasicMaterial::HasBaseColor() const
{
return m_basicUniformOffsets.baseColor != MaterialSettings::InvalidIndex;
}
inline bool BasicMaterial::HasBaseColorMap() const
{
return m_basicTextureIndexes.baseColor != MaterialSettings::InvalidIndex;
}
inline void BasicMaterial::SetAlphaMap(std::shared_ptr<Texture> alphaMap)
{
NazaraAssert(HasAlphaMap(), "Material has no alpha map slot");
bool hasAlphaMap = (alphaMap != nullptr);
m_material.SetTexture(m_basicTextureIndexes.alpha, std::move(alphaMap));
if (m_basicOptionIndexes.hasBaseColorMap != MaterialSettings::InvalidIndex)
m_material.SetOptionValue(m_basicOptionIndexes.hasAlphaMap, hasAlphaMap);
}
inline void BasicMaterial::SetAlphaSampler(TextureSamplerInfo alphaSampler)
{
NazaraAssert(HasAlphaMap(), "Material has no alpha map slot");
m_material.SetTextureSampler(m_basicTextureIndexes.alpha, std::move(alphaSampler));
}
inline void BasicMaterial::SetBaseColorMap(std::shared_ptr<Texture> baseColorMap)
{
NazaraAssert(HasBaseColorMap(), "Material has no diffuse map slot");
bool hasBaseColorMap = (baseColorMap != nullptr);
m_material.SetTexture(m_basicTextureIndexes.baseColor, std::move(baseColorMap));
if (m_basicOptionIndexes.hasBaseColorMap != MaterialSettings::InvalidIndex)
m_material.SetOptionValue(m_basicOptionIndexes.hasBaseColorMap, hasBaseColorMap);
}
inline void BasicMaterial::SetBaseColorSampler(TextureSamplerInfo diffuseSampler)
{
NazaraAssert(HasBaseColorMap(), "Material has no diffuse map slot");
m_material.SetTextureSampler(m_basicTextureIndexes.baseColor, std::move(diffuseSampler));
}
inline MaterialPass& BasicMaterial::GetMaterial()
{
return m_material;
}
inline const MaterialPass& BasicMaterial::GetMaterial() const
{
return m_material;
}
inline const std::shared_ptr<MaterialSettings>& BasicMaterial::GetSettings()
{
return s_basicMaterialSettings;
}
inline auto BasicMaterial::GetOffsets() -> const BasicUniformOffsets&
{
return s_basicUniformOffsets;
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -1,38 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_DEPTHMATERIAL_HPP
#define NAZARA_GRAPHICS_DEPTHMATERIAL_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/BasicMaterial.hpp>
namespace Nz
{
class NAZARA_GRAPHICS_API DepthMaterial : public BasicMaterial
{
friend class MaterialPipeline;
public:
using BasicMaterial::BasicMaterial;
~DepthMaterial() = default;
static inline const std::shared_ptr<MaterialSettings>& GetSettings();
protected:
static std::vector<std::shared_ptr<UberShader>> BuildShaders();
private:
static bool Initialize();
static void Uninitialize();
static std::shared_ptr<MaterialSettings> s_depthMaterialSettings;
};
}
#include <Nazara/Graphics/DepthMaterial.inl>
#endif // NAZARA_GRAPHICS_DEPTHMATERIAL_HPP

View File

@ -11,6 +11,7 @@
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/ElementRenderer.hpp> #include <Nazara/Graphics/ElementRenderer.hpp>
#include <Nazara/Graphics/FramePipelinePass.hpp> #include <Nazara/Graphics/FramePipelinePass.hpp>
#include <Nazara/Graphics/MaterialInstance.hpp>
#include <Nazara/Graphics/MaterialPass.hpp> #include <Nazara/Graphics/MaterialPass.hpp>
#include <Nazara/Graphics/RenderElement.hpp> #include <Nazara/Graphics/RenderElement.hpp>
#include <Nazara/Graphics/RenderElementOwner.hpp> #include <Nazara/Graphics/RenderElementOwner.hpp>
@ -24,7 +25,6 @@ namespace Nz
class ElementRendererRegistry; class ElementRendererRegistry;
class FrameGraph; class FrameGraph;
class FramePipeline; class FramePipeline;
class Material;
class NAZARA_GRAPHICS_API DepthPipelinePass : public FramePipelinePass class NAZARA_GRAPHICS_API DepthPipelinePass : public FramePipelinePass
{ {
@ -32,17 +32,17 @@ namespace Nz
DepthPipelinePass(FramePipeline& owner, ElementRendererRegistry& elementRegistry, AbstractViewer* viewer); DepthPipelinePass(FramePipeline& owner, ElementRendererRegistry& elementRegistry, AbstractViewer* viewer);
DepthPipelinePass(const DepthPipelinePass&) = delete; DepthPipelinePass(const DepthPipelinePass&) = delete;
DepthPipelinePass(DepthPipelinePass&&) = delete; DepthPipelinePass(DepthPipelinePass&&) = delete;
~DepthPipelinePass(); ~DepthPipelinePass() = default;
inline void InvalidateCommandBuffers(); inline void InvalidateCommandBuffers();
inline void InvalidateElements(); inline void InvalidateElements();
void Prepare(RenderFrame& renderFrame, const Frustumf& frustum, const std::vector<FramePipelinePass::VisibleRenderable>& visibleRenderables, std::size_t visibilityHash); void Prepare(RenderFrame& renderFrame, const Frustumf& frustum, const std::vector<FramePipelinePass::VisibleRenderable>& visibleRenderables, std::size_t visibilityHash);
void RegisterMaterial(const Material& material); void RegisterMaterialInstance(const MaterialInstance& materialInstance);
void RegisterToFrameGraph(FrameGraph& frameGraph, std::size_t depthBufferIndex); void RegisterToFrameGraph(FrameGraph& frameGraph, std::size_t depthBufferIndex);
void UnregisterMaterial(const Material& material); void UnregisterMaterialInstance(const MaterialInstance& materialInstance);
DepthPipelinePass& operator=(const DepthPipelinePass&) = delete; DepthPipelinePass& operator=(const DepthPipelinePass&) = delete;
DepthPipelinePass& operator=(DepthPipelinePass&&) = delete; DepthPipelinePass& operator=(DepthPipelinePass&&) = delete;
@ -52,8 +52,8 @@ namespace Nz
{ {
std::size_t usedCount = 1; std::size_t usedCount = 1;
NazaraSlot(MaterialPass, OnMaterialPassPipelineInvalidated, onMaterialPipelineInvalidated); NazaraSlot(MaterialInstance, OnMaterialInstancePipelineInvalidated, onMaterialInstancePipelineInvalidated);
NazaraSlot(MaterialPass, OnMaterialPassShaderBindingInvalidated, onMaterialShaderBindingInvalidated); NazaraSlot(MaterialInstance, OnMaterialInstanceShaderBindingInvalidated, onMaterialInstanceShaderBindingInvalidated);
}; };
std::size_t m_depthPassIndex; std::size_t m_depthPassIndex;
@ -61,7 +61,7 @@ namespace Nz
std::vector<std::unique_ptr<ElementRendererData>> m_elementRendererData; std::vector<std::unique_ptr<ElementRendererData>> m_elementRendererData;
std::vector<ElementRenderer::RenderStates> m_renderStates; std::vector<ElementRenderer::RenderStates> m_renderStates;
std::vector<RenderElementOwner> m_renderElements; std::vector<RenderElementOwner> m_renderElements;
std::unordered_map<MaterialPass*, MaterialPassEntry> m_materialPasses; std::unordered_map<const MaterialInstance*, MaterialPassEntry> m_materialInstances;
RenderQueue<const RenderElement*> m_renderQueue; RenderQueue<const RenderElement*> m_renderQueue;
RenderQueueRegistry m_renderQueueRegistry; RenderQueueRegistry m_renderQueueRegistry;
AbstractViewer* m_viewer; AbstractViewer* m_viewer;

View File

@ -41,6 +41,27 @@ namespace Nz
Volume Volume
}; };
enum class MaterialPropertyType
{
Bool,
Bool2,
Bool3,
Bool4,
Color,
Float,
Float2,
Float3,
Float4,
Int,
Int2,
Int3,
Int4,
UInt,
UInt2,
UInt3,
UInt4
};
enum class MaterialLightingType enum class MaterialLightingType
{ {
None, None,
@ -69,7 +90,7 @@ namespace Nz
Perspective Perspective
}; };
enum class PredefinedShaderBinding enum class EngineShaderBinding
{ {
InstanceDataUbo, InstanceDataUbo,
LightDataUbo, LightDataUbo,
@ -80,7 +101,7 @@ namespace Nz
Max = ViewerDataUbo Max = ViewerDataUbo
}; };
constexpr std::size_t PredefinedShaderBindingCount = static_cast<std::size_t>(PredefinedShaderBinding::Max) + 1; constexpr std::size_t PredefinedShaderBindingCount = static_cast<std::size_t>(EngineShaderBinding::Max) + 1;
} }
#endif // NAZARA_GRAPHICS_ENUMS_HPP #endif // NAZARA_GRAPHICS_ENUMS_HPP

View File

@ -21,6 +21,7 @@
#include <Nazara/Graphics/RenderElement.hpp> #include <Nazara/Graphics/RenderElement.hpp>
#include <Nazara/Graphics/RenderQueue.hpp> #include <Nazara/Graphics/RenderQueue.hpp>
#include <Nazara/Graphics/RenderQueueRegistry.hpp> #include <Nazara/Graphics/RenderQueueRegistry.hpp>
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Renderer/ShaderBinding.hpp> #include <Nazara/Renderer/ShaderBinding.hpp>
#include <Nazara/Utils/MemoryPool.hpp> #include <Nazara/Utils/MemoryPool.hpp>
#include <memory> #include <memory>
@ -42,12 +43,7 @@ namespace Nz
ForwardFramePipeline(ForwardFramePipeline&&) = delete; ForwardFramePipeline(ForwardFramePipeline&&) = delete;
~ForwardFramePipeline(); ~ForwardFramePipeline();
void InvalidateSkeletalInstance(std::size_t skeletalInstanceIndex) override;
void InvalidateViewer(std::size_t viewerIndex) override;
void InvalidateWorldInstance(std::size_t renderableIndex) override;
std::size_t RegisterLight(std::shared_ptr<Light> light, UInt32 renderMask) override; std::size_t RegisterLight(std::shared_ptr<Light> light, UInt32 renderMask) override;
void RegisterMaterialPass(MaterialPass* materialPass) override;
std::size_t RegisterRenderable(std::size_t worldInstanceIndex, std::size_t skeletonInstanceIndex, const InstancedRenderable* instancedRenderable, UInt32 renderMask, const Recti& scissorBox) override; std::size_t RegisterRenderable(std::size_t worldInstanceIndex, std::size_t skeletonInstanceIndex, const InstancedRenderable* instancedRenderable, UInt32 renderMask, const Recti& scissorBox) override;
std::size_t RegisterSkeleton(SkeletonInstancePtr skeletonInstance) override; std::size_t RegisterSkeleton(SkeletonInstancePtr skeletonInstance) override;
std::size_t RegisterViewer(AbstractViewer* viewerInstance, Int32 renderOrder) override; std::size_t RegisterViewer(AbstractViewer* viewerInstance, Int32 renderOrder) override;
@ -56,7 +52,6 @@ namespace Nz
void Render(RenderFrame& renderFrame) override; void Render(RenderFrame& renderFrame) override;
void UnregisterLight(std::size_t lightIndex) override; void UnregisterLight(std::size_t lightIndex) override;
void UnregisterMaterialPass(MaterialPass* material) override;
void UnregisterRenderable(std::size_t renderableIndex) override; void UnregisterRenderable(std::size_t renderableIndex) override;
void UnregisterSkeleton(std::size_t skeletonIndex) override; void UnregisterSkeleton(std::size_t skeletonIndex) override;
void UnregisterViewer(std::size_t viewerIndex) override; void UnregisterViewer(std::size_t viewerIndex) override;
@ -73,6 +68,9 @@ namespace Nz
private: private:
BakedFrameGraph BuildFrameGraph(); BakedFrameGraph BuildFrameGraph();
void RegisterMaterialInstance(MaterialInstance* materialPass);
void UnregisterMaterialInstance(MaterialInstance* material);
struct ViewerData; struct ViewerData;
struct LightData struct LightData
@ -83,11 +81,11 @@ namespace Nz
NazaraSlot(Light, OnLightDataInvalided, onLightInvalidated); NazaraSlot(Light, OnLightDataInvalided, onLightInvalidated);
}; };
struct MaterialPassData struct MaterialInstanceData
{ {
std::size_t usedCount = 0; std::size_t usedCount = 0;
NazaraSlot(MaterialPass, OnMaterialPassInvalidated, onMaterialPassInvalided); NazaraSlot(TransferInterface, OnTransferRequired, onTransferRequired);
}; };
struct RenderableData struct RenderableData
@ -109,6 +107,13 @@ namespace Nz
ShaderBindingPtr blitShaderBinding; ShaderBindingPtr blitShaderBinding;
}; };
struct SkeletonInstanceData
{
SkeletonInstancePtr skeleton;
NazaraSlot(TransferInterface, OnTransferRequired, onTransferRequired);
};
struct ViewerData struct ViewerData
{ {
std::size_t forwardColorAttachment; std::size_t forwardColorAttachment;
@ -122,27 +127,33 @@ namespace Nz
RenderQueueRegistry forwardRegistry; RenderQueueRegistry forwardRegistry;
RenderQueue<RenderElement*> forwardRenderQueue; RenderQueue<RenderElement*> forwardRenderQueue;
ShaderBindingPtr blitShaderBinding; ShaderBindingPtr blitShaderBinding;
NazaraSlot(TransferInterface, OnTransferRequired, onTransferRequired);
};
struct WorldInstanceData
{
WorldInstancePtr worldInstance;
NazaraSlot(TransferInterface, OnTransferRequired, onTransferRequired);
}; };
std::unordered_map<MaterialPass*, MaterialPassData> m_activeMaterialPasses;
std::unordered_map<const RenderTarget*, RenderTargetData> m_renderTargets; std::unordered_map<const RenderTarget*, RenderTargetData> m_renderTargets;
std::unordered_set<MaterialPass*> m_invalidatedMaterialPasses; std::unordered_map<MaterialInstance*, MaterialInstanceData> m_materialInstances;
std::vector<ElementRenderer::RenderStates> m_renderStates; std::vector<ElementRenderer::RenderStates> m_renderStates;
std::vector<FramePipelinePass::VisibleRenderable> m_visibleRenderables; std::vector<FramePipelinePass::VisibleRenderable> m_visibleRenderables;
std::vector<const Light*> m_visibleLights; std::vector<const Light*> m_visibleLights;
robin_hood::unordered_set<TransferInterface*> m_transferSet;
BakedFrameGraph m_bakedFrameGraph; BakedFrameGraph m_bakedFrameGraph;
Bitset<UInt64> m_invalidatedSkeletonInstances;
Bitset<UInt64> m_invalidatedViewerInstances;
Bitset<UInt64> m_invalidatedWorldInstances;
Bitset<UInt64> m_removedSkeletonInstances; Bitset<UInt64> m_removedSkeletonInstances;
Bitset<UInt64> m_removedViewerInstances; Bitset<UInt64> m_removedViewerInstances;
Bitset<UInt64> m_removedWorldInstances; Bitset<UInt64> m_removedWorldInstances;
ElementRendererRegistry& m_elementRegistry; ElementRendererRegistry& m_elementRegistry;
MemoryPool<RenderableData> m_renderablePool; MemoryPool<RenderableData> m_renderablePool;
MemoryPool<LightData> m_lightPool; MemoryPool<LightData> m_lightPool;
MemoryPool<SkeletonInstancePtr> m_skeletonInstances; MemoryPool<SkeletonInstanceData> m_skeletonInstances;
MemoryPool<ViewerData> m_viewerPool; MemoryPool<ViewerData> m_viewerPool;
MemoryPool<WorldInstancePtr> m_worldInstances; MemoryPool<WorldInstanceData> m_worldInstances;
RenderFrame* m_currentRenderFrame; RenderFrame* m_currentRenderFrame;
bool m_rebuildFrameGraph; bool m_rebuildFrameGraph;
}; };

View File

@ -12,6 +12,7 @@
#include <Nazara/Graphics/ElementRenderer.hpp> #include <Nazara/Graphics/ElementRenderer.hpp>
#include <Nazara/Graphics/FramePipelinePass.hpp> #include <Nazara/Graphics/FramePipelinePass.hpp>
#include <Nazara/Graphics/Light.hpp> #include <Nazara/Graphics/Light.hpp>
#include <Nazara/Graphics/MaterialInstance.hpp>
#include <Nazara/Graphics/MaterialPass.hpp> #include <Nazara/Graphics/MaterialPass.hpp>
#include <Nazara/Graphics/RenderElement.hpp> #include <Nazara/Graphics/RenderElement.hpp>
#include <Nazara/Graphics/RenderElementOwner.hpp> #include <Nazara/Graphics/RenderElementOwner.hpp>
@ -27,7 +28,6 @@ namespace Nz
class FrameGraph; class FrameGraph;
class FramePipeline; class FramePipeline;
class Light; class Light;
class Material;
class NAZARA_GRAPHICS_API ForwardPipelinePass : public FramePipelinePass class NAZARA_GRAPHICS_API ForwardPipelinePass : public FramePipelinePass
{ {
@ -35,17 +35,17 @@ namespace Nz
ForwardPipelinePass(FramePipeline& owner, ElementRendererRegistry& elementRegistry, AbstractViewer* viewer); ForwardPipelinePass(FramePipeline& owner, ElementRendererRegistry& elementRegistry, AbstractViewer* viewer);
ForwardPipelinePass(const ForwardPipelinePass&) = delete; ForwardPipelinePass(const ForwardPipelinePass&) = delete;
ForwardPipelinePass(ForwardPipelinePass&&) = delete; ForwardPipelinePass(ForwardPipelinePass&&) = delete;
~ForwardPipelinePass(); ~ForwardPipelinePass() = default;
inline void InvalidateCommandBuffers(); inline void InvalidateCommandBuffers();
inline void InvalidateElements(); inline void InvalidateElements();
void Prepare(RenderFrame& renderFrame, const Frustumf& frustum, const std::vector<FramePipelinePass::VisibleRenderable>& visibleRenderables, const std::vector<const Light*>& visibleLights, std::size_t visibilityHash); void Prepare(RenderFrame& renderFrame, const Frustumf& frustum, const std::vector<FramePipelinePass::VisibleRenderable>& visibleRenderables, const std::vector<const Light*>& visibleLights, std::size_t visibilityHash);
void RegisterMaterial(const Material& material); void RegisterMaterialInstance(const MaterialInstance& material);
void RegisterToFrameGraph(FrameGraph& frameGraph, std::size_t colorBufferIndex, std::size_t depthBufferIndex, bool hasDepthPrepass); void RegisterToFrameGraph(FrameGraph& frameGraph, std::size_t colorBufferIndex, std::size_t depthBufferIndex, bool hasDepthPrepass);
void UnregisterMaterial(const Material& material); void UnregisterMaterialInstance(const MaterialInstance& material);
ForwardPipelinePass& operator=(const ForwardPipelinePass&) = delete; ForwardPipelinePass& operator=(const ForwardPipelinePass&) = delete;
ForwardPipelinePass& operator=(ForwardPipelinePass&&) = delete; ForwardPipelinePass& operator=(ForwardPipelinePass&&) = delete;
@ -57,8 +57,8 @@ namespace Nz
{ {
std::size_t usedCount = 1; std::size_t usedCount = 1;
NazaraSlot(MaterialPass, OnMaterialPassPipelineInvalidated, onMaterialPipelineInvalidated); NazaraSlot(MaterialInstance, OnMaterialInstancePipelineInvalidated, onMaterialInstancePipelineInvalidated);
NazaraSlot(MaterialPass, OnMaterialPassShaderBindingInvalidated, onMaterialShaderBindingInvalidated); NazaraSlot(MaterialInstance, OnMaterialInstanceShaderBindingInvalidated, onMaterialInstanceShaderBindingInvalidated);
}; };
using LightKey = std::array<const Light*, MaxLightCountPerDraw>; using LightKey = std::array<const Light*, MaxLightCountPerDraw>;
@ -86,7 +86,7 @@ namespace Nz
std::vector<std::unique_ptr<ElementRendererData>> m_elementRendererData; std::vector<std::unique_ptr<ElementRendererData>> m_elementRendererData;
std::vector<ElementRenderer::RenderStates> m_renderStates; std::vector<ElementRenderer::RenderStates> m_renderStates;
std::vector<RenderElementOwner> m_renderElements; std::vector<RenderElementOwner> m_renderElements;
std::unordered_map<MaterialPass*, MaterialPassEntry> m_materialPasses; std::unordered_map<const MaterialInstance*, MaterialPassEntry> m_materialInstances;
std::unordered_map<const RenderElement*, RenderBufferView> m_lightPerRenderElement; std::unordered_map<const RenderElement*, RenderBufferView> m_lightPerRenderElement;
std::unordered_map<LightKey, RenderBufferView, LightKeyHasher> m_lightBufferPerLights; std::unordered_map<LightKey, RenderBufferView, LightKeyHasher> m_lightBufferPerLights;
std::vector<LightDataUbo> m_lightDataBuffers; std::vector<LightDataUbo> m_lightDataBuffers;

View File

@ -21,7 +21,6 @@ namespace Nz
class AbstractViewer; class AbstractViewer;
class InstancedRenderable; class InstancedRenderable;
class Light; class Light;
class MaterialPass;
class RenderFrame; class RenderFrame;
class NAZARA_GRAPHICS_API FramePipeline class NAZARA_GRAPHICS_API FramePipeline
@ -34,12 +33,7 @@ namespace Nz
inline DebugDrawer& GetDebugDrawer(); inline DebugDrawer& GetDebugDrawer();
virtual void InvalidateSkeletalInstance(std::size_t skeletalInstanceIndex) = 0;
virtual void InvalidateViewer(std::size_t viewerIndex) = 0;
virtual void InvalidateWorldInstance(std::size_t worldInstance) = 0;
virtual std::size_t RegisterLight(std::shared_ptr<Light> light, UInt32 renderMask) = 0; virtual std::size_t RegisterLight(std::shared_ptr<Light> light, UInt32 renderMask) = 0;
virtual void RegisterMaterialPass(MaterialPass* materialPass) = 0;
virtual std::size_t RegisterRenderable(std::size_t worldInstanceIndex, std::size_t skeletonInstanceIndex, const InstancedRenderable* instancedRenderable, UInt32 renderMask, const Recti& scissorBox) = 0; virtual std::size_t RegisterRenderable(std::size_t worldInstanceIndex, std::size_t skeletonInstanceIndex, const InstancedRenderable* instancedRenderable, UInt32 renderMask, const Recti& scissorBox) = 0;
virtual std::size_t RegisterSkeleton(SkeletonInstancePtr skeletonInstance) = 0; virtual std::size_t RegisterSkeleton(SkeletonInstancePtr skeletonInstance) = 0;
virtual std::size_t RegisterViewer(AbstractViewer* viewerInstance, Int32 renderOrder) = 0; virtual std::size_t RegisterViewer(AbstractViewer* viewerInstance, Int32 renderOrder) = 0;
@ -48,7 +42,6 @@ namespace Nz
virtual void Render(RenderFrame& renderFrame) = 0; virtual void Render(RenderFrame& renderFrame) = 0;
virtual void UnregisterLight(std::size_t lightIndex) = 0; virtual void UnregisterLight(std::size_t lightIndex) = 0;
virtual void UnregisterMaterialPass(MaterialPass* materialPass) = 0;
virtual void UnregisterRenderable(std::size_t renderableIndex) = 0; virtual void UnregisterRenderable(std::size_t renderableIndex) = 0;
virtual void UnregisterSkeleton(std::size_t skeletonIndex) = 0; virtual void UnregisterSkeleton(std::size_t skeletonIndex) = 0;
virtual void UnregisterViewer(std::size_t viewerIndex) = 0; virtual void UnregisterViewer(std::size_t viewerIndex) = 0;

View File

@ -10,6 +10,7 @@
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/Material.hpp> #include <Nazara/Graphics/Material.hpp>
#include <Nazara/Graphics/MaterialInstance.hpp>
#include <Nazara/Graphics/MaterialPassRegistry.hpp> #include <Nazara/Graphics/MaterialPassRegistry.hpp>
#include <Nazara/Graphics/TextureSamplerCache.hpp> #include <Nazara/Graphics/TextureSamplerCache.hpp>
#include <Nazara/Renderer/RenderDevice.hpp> #include <Nazara/Renderer/RenderDevice.hpp>
@ -43,8 +44,10 @@ namespace Nz
inline const DefaultTextures& GetDefaultTextures() const; inline const DefaultTextures& GetDefaultTextures() const;
inline MaterialPassRegistry& GetMaterialPassRegistry(); inline MaterialPassRegistry& GetMaterialPassRegistry();
inline const MaterialPassRegistry& GetMaterialPassRegistry() const; inline const MaterialPassRegistry& GetMaterialPassRegistry() const;
MaterialLoader& GetMaterialLoader(); inline MaterialInstanceLoader& GetMaterialInstanceLoader();
const MaterialLoader& GetMaterialLoader() const; inline const MaterialInstanceLoader& GetMaterialInstanceLoader() const;
inline MaterialLoader& GetMaterialLoader();
inline const MaterialLoader& GetMaterialLoader() const;
inline PixelFormat GetPreferredDepthStencilFormat() const; inline PixelFormat GetPreferredDepthStencilFormat() const;
inline const std::shared_ptr<RenderDevice>& GetRenderDevice() const; inline const std::shared_ptr<RenderDevice>& GetRenderDevice() const;
inline const RenderPassCache& GetRenderPassCache() const; inline const RenderPassCache& GetRenderPassCache() const;
@ -59,8 +62,13 @@ namespace Nz
struct DefaultMaterials struct DefaultMaterials
{ {
std::shared_ptr<Material> depthMaterial; std::shared_ptr<Material> basicMaterial;
std::shared_ptr<Material> noDepthMaterial; std::shared_ptr<Material> phongMaterial;
std::shared_ptr<Material> pbrMaterial;
std::shared_ptr<MaterialInstance> basicDefault;
std::shared_ptr<MaterialInstance> basicNoDepth;
std::shared_ptr<MaterialInstance> basicTransparent;
}; };
struct DefaultTextures struct DefaultTextures
@ -86,6 +94,7 @@ namespace Nz
std::shared_ptr<RenderPipelineLayout> m_blitPipelineLayout; std::shared_ptr<RenderPipelineLayout> m_blitPipelineLayout;
DefaultMaterials m_defaultMaterials; DefaultMaterials m_defaultMaterials;
DefaultTextures m_defaultTextures; DefaultTextures m_defaultTextures;
MaterialInstanceLoader m_materialInstanceLoader;
MaterialLoader m_materialLoader; MaterialLoader m_materialLoader;
MaterialPassRegistry m_materialPassRegistry; MaterialPassRegistry m_materialPassRegistry;
PixelFormat m_preferredDepthStencilFormat; PixelFormat m_preferredDepthStencilFormat;

View File

@ -37,6 +37,16 @@ namespace Nz
return m_materialPassRegistry; return m_materialPassRegistry;
} }
inline MaterialInstanceLoader& Graphics::GetMaterialInstanceLoader()
{
return m_materialInstanceLoader;
}
inline const MaterialInstanceLoader& Graphics::GetMaterialInstanceLoader() const
{
return m_materialInstanceLoader;
}
inline MaterialLoader& Graphics::GetMaterialLoader() inline MaterialLoader& Graphics::GetMaterialLoader()
{ {
return m_materialLoader; return m_materialLoader;

View File

@ -18,7 +18,7 @@ namespace Nz
{ {
class CommandBufferBuilder; class CommandBufferBuilder;
class ElementRendererRegistry; class ElementRendererRegistry;
class Material; class MaterialInstance;
class RenderElement; class RenderElement;
class SkeletonInstance; class SkeletonInstance;
class WorldInstance; class WorldInstance;
@ -36,7 +36,7 @@ namespace Nz
virtual void BuildElement(ElementRendererRegistry& registry, const ElementData& elementData, std::size_t passIndex, std::vector<RenderElementOwner>& elements) const = 0; virtual void BuildElement(ElementRendererRegistry& registry, const ElementData& elementData, std::size_t passIndex, std::vector<RenderElementOwner>& elements) const = 0;
inline const Boxf& GetAABB() const; inline const Boxf& GetAABB() const;
virtual const std::shared_ptr<Material>& GetMaterial(std::size_t i) const = 0; virtual const std::shared_ptr<MaterialInstance>& GetMaterial(std::size_t i) const = 0;
virtual std::size_t GetMaterialCount() const = 0; virtual std::size_t GetMaterialCount() const = 0;
inline int GetRenderLayer() const; inline int GetRenderLayer() const;
@ -47,7 +47,7 @@ namespace Nz
NazaraSignal(OnAABBUpdate, InstancedRenderable* /*instancedRenderable*/, const Boxf& /*aabb*/); NazaraSignal(OnAABBUpdate, InstancedRenderable* /*instancedRenderable*/, const Boxf& /*aabb*/);
NazaraSignal(OnElementInvalidated, InstancedRenderable* /*instancedRenderable*/); NazaraSignal(OnElementInvalidated, InstancedRenderable* /*instancedRenderable*/);
NazaraSignal(OnMaterialInvalidated, InstancedRenderable* /*instancedRenderable*/, std::size_t /*materialIndex*/, const std::shared_ptr<Material>& /*newMaterial*/); NazaraSignal(OnMaterialInvalidated, InstancedRenderable* /*instancedRenderable*/, std::size_t /*materialIndex*/, const std::shared_ptr<MaterialInstance>& /*newMaterial*/);
struct ElementData struct ElementData
{ {

View File

@ -23,7 +23,7 @@ namespace Nz
enum class Orientation; enum class Orientation;
struct Section; struct Section;
LinearSlicedSprite(std::shared_ptr<Material> material, Orientation orientation); LinearSlicedSprite(std::shared_ptr<MaterialInstance> material, Orientation orientation);
LinearSlicedSprite(const LinearSlicedSprite&) = delete; LinearSlicedSprite(const LinearSlicedSprite&) = delete;
LinearSlicedSprite(LinearSlicedSprite&&) noexcept = default; LinearSlicedSprite(LinearSlicedSprite&&) noexcept = default;
~LinearSlicedSprite() = default; ~LinearSlicedSprite() = default;
@ -35,7 +35,7 @@ namespace Nz
inline void Clear(); inline void Clear();
inline const Color& GetColor() const; inline const Color& GetColor() const;
const std::shared_ptr<Material>& GetMaterial(std::size_t i = 0) const override; const std::shared_ptr<MaterialInstance>& GetMaterial(std::size_t i = 0) const override;
std::size_t GetMaterialCount() const override; std::size_t GetMaterialCount() const override;
inline Orientation GetOrientation() const; inline Orientation GetOrientation() const;
inline const Section& GetSection(std::size_t sectionIndex) const; inline const Section& GetSection(std::size_t sectionIndex) const;
@ -46,7 +46,7 @@ namespace Nz
inline void RemoveSection(std::size_t sectionIndex); inline void RemoveSection(std::size_t sectionIndex);
inline void SetColor(const Color& color); inline void SetColor(const Color& color);
inline void SetMaterial(std::shared_ptr<Material> material); inline void SetMaterial(std::shared_ptr<MaterialInstance> material);
inline void SetSection(std::size_t sectionIndex, float size, float textureCoord); inline void SetSection(std::size_t sectionIndex, float size, float textureCoord);
inline void SetSectionSize(std::size_t sectionIndex, float size); inline void SetSectionSize(std::size_t sectionIndex, float size);
inline void SetSectionTextureCoord(std::size_t sectionIndex, float textureCoord); inline void SetSectionTextureCoord(std::size_t sectionIndex, float textureCoord);
@ -76,7 +76,7 @@ namespace Nz
std::array<Section, MaxSection> m_sections; std::array<Section, MaxSection> m_sections;
std::array<VertexStruct_XYZ_Color_UV, 4 * MaxSection> m_vertices; std::array<VertexStruct_XYZ_Color_UV, 4 * MaxSection> m_vertices;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::size_t m_sectionCount; std::size_t m_sectionCount;
std::size_t m_spriteCount; std::size_t m_spriteCount;
Color m_color; Color m_color;

View File

@ -71,7 +71,7 @@ namespace Nz
UpdateVertices(); UpdateVertices();
} }
inline void LinearSlicedSprite::SetMaterial(std::shared_ptr<Material> material) inline void LinearSlicedSprite::SetMaterial(std::shared_ptr<MaterialInstance> material)
{ {
assert(material); assert(material);

View File

@ -14,50 +14,91 @@
#include <Nazara/Core/ResourceSaver.hpp> #include <Nazara/Core/ResourceSaver.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/Enums.hpp> #include <Nazara/Graphics/Enums.hpp>
#include <Nazara/Graphics/MaterialSettings.hpp>
#include <Nazara/Graphics/RenderBufferPool.hpp>
#include <Nazara/Graphics/ShaderReflection.hpp>
#include <NZSL/Ast/Module.hpp>
#include <array>
#include <memory>
#include <unordered_map>
namespace Nz namespace Nz
{ {
struct NAZARA_GRAPHICS_API MaterialParams : ResourceParameters struct NAZARA_GRAPHICS_API MaterialParams : ResourceParameters
{ {
MaterialLightingType lightingType = MaterialLightingType::None;
bool IsValid() const; bool IsValid() const;
}; };
class Material; class Material;
class MaterialPass; class MaterialInstance;
class RenderPipelineLayout;
using MaterialLibrary = ObjectLibrary<Material>; using MaterialLibrary = ObjectLibrary<Material>;
using MaterialLoader = ResourceLoader<Material, MaterialParams>; using MaterialLoader = ResourceLoader<Material, MaterialParams>;
using MaterialManager = ResourceManager<Material, MaterialParams>; using MaterialManager = ResourceManager<Material, MaterialParams>;
using MaterialSaver = ResourceSaver<Material, MaterialParams>; using MaterialSaver = ResourceSaver<Material, MaterialParams>;
class NAZARA_GRAPHICS_API Material : public Resource class NAZARA_GRAPHICS_API Material : public Resource, public std::enable_shared_from_this<Material>
{ {
public: public:
Material() = default; struct TextureData;
struct UniformBlockData;
Material(MaterialSettings settings, const std::string& referenceModuleName);
Material(MaterialSettings settings, const nzsl::Ast::ModulePtr& referenceModule);
~Material() = default; ~Material() = default;
inline void AddPass(std::size_t passIndex, std::shared_ptr<MaterialPass> pass); std::shared_ptr<MaterialInstance> CreateInstance() const;
void AddPass(std::string passName, std::shared_ptr<MaterialPass> pass);
const std::shared_ptr<MaterialPass>& FindPass(const std::string& passName) const; std::shared_ptr<MaterialInstance> GetDefaultInstance() const;
template<typename F> void ForEachPass(F&& callback); inline std::size_t FindTextureByTag(const std::string& tag) const;
inline std::size_t FindUniformBlockByTag(const std::string& tag) const;
inline const std::shared_ptr<MaterialPass>& GetPass(std::size_t passIndex) const; inline UInt32 GetEngineBindingIndex(EngineShaderBinding shaderBinding) const;
inline const std::shared_ptr<RenderPipelineLayout>& GetRenderPipelineLayout() const;
inline bool HasPass(std::size_t passIndex) const; inline const MaterialSettings& GetSettings() const;
inline const TextureData& GetTextureData(std::size_t textureIndex) const;
inline void RemovePass(std::size_t passIndex); inline std::size_t GetTextureCount() const;
void RemovePass(const std::string& passName); inline const UniformBlockData& GetUniformBlockData(std::size_t uniformBlockIndex) const;
inline std::size_t GetUniformBlockCount() const;
static std::shared_ptr<Material> Build(const ParameterList& materialData);
static std::shared_ptr<Material> LoadFromFile(const std::filesystem::path& filePath, const MaterialParams& params = MaterialParams()); static std::shared_ptr<Material> LoadFromFile(const std::filesystem::path& filePath, const MaterialParams& params = MaterialParams());
static std::shared_ptr<Material> LoadFromMemory(const void* data, std::size_t size, const MaterialParams& params = MaterialParams()); static std::shared_ptr<Material> LoadFromMemory(const void* data, std::size_t size, const MaterialParams& params = MaterialParams());
static std::shared_ptr<Material> LoadFromStream(Stream& stream, const MaterialParams& params = MaterialParams()); static std::shared_ptr<Material> LoadFromStream(Stream& stream, const MaterialParams& params = MaterialParams());
static inline ImageType ToImageType(nzsl::ImageType imageType);
static constexpr UInt32 InvalidBindingIndex = std::numeric_limits<UInt32>::max();
static constexpr std::size_t InvalidIndex = std::numeric_limits<std::size_t>::max();
struct TextureData
{
UInt32 bindingSet;
UInt32 bindingIndex;
ImageType imageType;
};
struct UniformBlockData
{
UInt32 bindingSet;
UInt32 bindingIndex;
std::size_t structIndex;
std::unique_ptr<RenderBufferPool> bufferPool;
};
private: private:
std::vector<std::shared_ptr<MaterialPass>> m_passes; std::array<UInt32, PredefinedShaderBindingCount> m_engineShaderBindings;
std::shared_ptr<RenderPipelineLayout> m_renderPipelineLayout;
std::unordered_map<UInt32, nzsl::Ast::ConstantSingleValue> m_optionValues;
std::unordered_map<std::string /*tag*/, std::size_t> m_textureByTag;
std::unordered_map<std::string /*tag*/, std::size_t> m_uniformBlockByTag;
std::vector<TextureData> m_textures;
std::vector<UniformBlockData> m_uniformBlocks;
mutable std::weak_ptr<MaterialInstance> m_defaultInstance;
MaterialSettings m_settings;
ShaderReflection m_reflection;
}; };
} }

View File

@ -7,49 +7,75 @@
namespace Nz namespace Nz
{ {
inline void Material::AddPass(std::size_t passIndex, std::shared_ptr<MaterialPass> pass) inline std::size_t Material::FindTextureByTag(const std::string& tag) const
{ {
if (passIndex >= m_passes.size()) auto it = m_textureByTag.find(tag);
m_passes.resize(passIndex + 1); if (it == m_textureByTag.end())
return InvalidIndex;
m_passes[passIndex] = std::move(pass); return it->second;
} }
template<typename F> inline std::size_t Material::FindUniformBlockByTag(const std::string& tag) const
void Material::ForEachPass(F&& callback)
{ {
for (std::size_t i = 0; i < m_passes.size(); ++i) auto it = m_uniformBlockByTag.find(tag);
{ if (it == m_uniformBlockByTag.end())
if (m_passes[i]) return InvalidIndex;
callback(i, m_passes[i]);
} return it->second;
} }
inline const std::shared_ptr<MaterialPass>& Material::GetPass(std::size_t passIndex) const inline UInt32 Material::GetEngineBindingIndex(EngineShaderBinding shaderBinding) const
{ {
if (passIndex >= m_passes.size()) return m_engineShaderBindings[UnderlyingCast(shaderBinding)];
}
inline const std::shared_ptr<RenderPipelineLayout>& Material::GetRenderPipelineLayout() const
{
return m_renderPipelineLayout;
}
inline const MaterialSettings& Material::GetSettings() const
{
return m_settings;
}
inline auto Material::GetTextureData(std::size_t textureIndex) const -> const TextureData&
{
assert(textureIndex < m_textures.size());
return m_textures[textureIndex];
}
inline std::size_t Material::GetTextureCount() const
{
return m_textures.size();
}
inline auto Material::GetUniformBlockData(std::size_t uniformBlockIndex) const -> const UniformBlockData&
{
assert(uniformBlockIndex < m_uniformBlocks.size());
return m_uniformBlocks[uniformBlockIndex];
}
inline std::size_t Material::GetUniformBlockCount() const
{
return m_uniformBlocks.size();
}
inline ImageType Material::ToImageType(nzsl::ImageType imageType)
{
switch (imageType)
{ {
static std::shared_ptr<MaterialPass> dummy; case nzsl::ImageType::E1D: return ImageType::E1D;
return dummy; case nzsl::ImageType::E1D_Array: return ImageType::E1D_Array;
case nzsl::ImageType::E2D: return ImageType::E2D;
case nzsl::ImageType::E2D_Array: return ImageType::E2D_Array;
case nzsl::ImageType::E3D: return ImageType::E3D;
case nzsl::ImageType::Cubemap: return ImageType::Cubemap;
} }
return m_passes[passIndex]; NazaraError("invalid image type 0x" + NumberToString(UnderlyingCast(imageType), 16));
} return ImageType::E2D;
inline bool Material::HasPass(std::size_t passIndex) const
{
if (passIndex >= m_passes.size())
return false;
return m_passes[passIndex] != nullptr;
}
inline void Material::RemovePass(std::size_t passIndex)
{
if (passIndex >= m_passes.size())
return;
m_passes[passIndex].reset();
} }
} }

View File

@ -0,0 +1,165 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_MATERIALINSTANCE_HPP
#define NAZARA_GRAPHICS_MATERIALINSTANCE_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/Enums.hpp>
#include <Nazara/Graphics/MaterialSettings.hpp>
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Renderer/RenderBufferView.hpp>
#include <Nazara/Renderer/ShaderBinding.hpp>
#include <Nazara/Utils/FunctionRef.hpp>
#include <NZSL/Ast/ConstantValue.hpp>
#include <memory>
#include <unordered_map>
#include <vector>
namespace Nz
{
struct NAZARA_GRAPHICS_API MaterialInstanceParams : ResourceParameters
{
MaterialLightingType lightingType = MaterialLightingType::None;
bool IsValid() const;
};
class Material;
class MaterialInstance;
class MaterialPipeline;
class Texture;
using MaterialInstanceLibrary = ObjectLibrary<MaterialInstance>;
using MaterialInstanceLoader = ResourceLoader<MaterialInstance, MaterialInstanceParams>;
using MaterialInstanceManager = ResourceManager<MaterialInstance, MaterialInstanceParams>;
using MaterialInstanceSaver = ResourceSaver<MaterialInstance, MaterialInstanceParams>;
class NAZARA_GRAPHICS_API MaterialInstance : public TransferInterface
{
struct CopyToken {};
public:
MaterialInstance(std::shared_ptr<const Material> parent);
MaterialInstance(const MaterialInstance&) = delete;
MaterialInstance(const MaterialInstance& material, CopyToken);
MaterialInstance(MaterialInstance&&) = delete;
~MaterialInstance();
inline std::shared_ptr<MaterialInstance> Clone() const;
void DisablePass(std::string_view passName);
inline void DisablePass(std::size_t passIndex);
void EnablePass(std::string_view passName, bool enable = true);
inline void EnablePass(std::size_t passIndex, bool enable = true);
void FillShaderBinding(std::vector<ShaderBinding::Binding>& bindings) const;
inline std::size_t FindTextureProperty(std::string_view propertyName) const;
inline std::size_t FindValueProperty(std::string_view propertyName) const;
inline const std::shared_ptr<const Material>& GetParentMaterial() const;
inline MaterialPassFlags GetPassFlags(std::size_t passIndex) const;
const std::shared_ptr<MaterialPipeline>& GetPipeline(std::size_t passIndex) const;
inline const std::shared_ptr<Texture>* GetTextureProperty(std::string_view propertyName) const;
inline const std::shared_ptr<Texture>& GetTextureProperty(std::size_t textureIndex) const;
inline const std::shared_ptr<Texture>& GetTexturePropertyOverride(std::size_t textureIndex) const;
inline const TextureSamplerInfo* GetTextureSamplerProperty(std::string_view propertyName) const;
inline const TextureSamplerInfo& GetTextureSamplerProperty(std::size_t textureIndex) const;
inline const MaterialSettings::Value* GetValueProperty(std::string_view propertyName) const;
inline const MaterialSettings::Value& GetValueProperty(std::size_t valueIndex) const;
inline const MaterialSettings::Value& GetValuePropertyOverride(std::size_t valueIndex) const;
bool HasPass(std::string_view passName) const;
inline bool HasPass(std::size_t passIndex) const;
void OnTransfer(RenderFrame& renderFrame, CommandBufferBuilder& builder) override;
inline void SetTextureProperty(std::string_view propertyName, std::shared_ptr<Texture> texture);
inline void SetTextureProperty(std::string_view propertyName, std::shared_ptr<Texture> texture, const TextureSamplerInfo& samplerInfo);
void SetTextureProperty(std::size_t textureIndex, std::shared_ptr<Texture> texture);
void SetTextureProperty(std::size_t textureIndex, std::shared_ptr<Texture> texture, const TextureSamplerInfo& samplerInfo);
inline void SetTextureSamplerProperty(std::string_view propertyName, const TextureSamplerInfo& samplerInfo);
void SetTextureSamplerProperty(std::size_t textureIndex, const TextureSamplerInfo& samplerInfo);
inline void SetValueProperty(std::string_view propertyName, const MaterialSettings::Value& value);
void SetValueProperty(std::size_t valueIndex, const MaterialSettings::Value& value);
void UpdateOptionValue(UInt32 optionHash, const nzsl::Ast::ConstantSingleValue& value);
void UpdatePassFlags(std::string_view passName, MaterialPassFlags materialFlags);
inline void UpdatePassFlags(std::size_t passName, MaterialPassFlags materialFlags);
void UpdatePassStates(std::string_view passName, FunctionRef<bool(RenderStates&)> stateUpdater);
template<typename F> void UpdatePassStates(std::size_t passIndex, F&& stateUpdater);
void UpdateTextureBinding(std::size_t textureBinding, std::shared_ptr<Texture> texture, std::shared_ptr<TextureSampler> textureSampler);
void UpdateUniformBufferData(std::size_t uniformBufferIndex, std::size_t offset, std::size_t size, const void* data);
MaterialInstance& operator=(const MaterialInstance&) = delete;
MaterialInstance& operator=(MaterialInstance&&) = delete;
static constexpr std::size_t InvalidPropertyIndex = MaterialSettings::InvalidPropertyIndex;
NazaraSignal(OnMaterialInstancePipelineInvalidated, const MaterialInstance* /*matInstance*/, std::size_t /*passIndex*/);
NazaraSignal(OnMaterialInstanceShaderBindingInvalidated, const MaterialInstance* /*matInstance*/);
private:
inline void InvalidatePassPipeline(std::size_t passIndex);
inline void InvalidateShaderBinding();
struct PassShader
{
std::shared_ptr<UberShader> shader;
NazaraSlot(UberShader, OnShaderUpdated, onShaderUpdated);
};
struct PassData
{
mutable MaterialPipelineInfo pipelineInfo;
mutable std::shared_ptr<MaterialPipeline> pipeline;
std::vector<PassShader> shaders;
MaterialPassFlags flags;
bool enabled = false;
};
struct TextureBinding
{
std::shared_ptr<Texture> texture;
std::shared_ptr<TextureSampler> sampler;
};
struct TextureProperty
{
std::shared_ptr<Texture> texture;
TextureSamplerInfo samplerInfo;
};
struct UniformBuffer
{
std::size_t bufferIndex;
std::vector<UInt8> values;
RenderBufferView bufferView;
bool dataInvalidated = true;
};
std::shared_ptr<const Material> m_parent;
std::unordered_map<UInt32, nzsl::Ast::ConstantSingleValue> m_optionValuesOverride;
std::vector<MaterialSettings::Value> m_valueOverride;
std::vector<PassData> m_passes;
std::vector<TextureBinding> m_textureBinding;
std::vector<TextureProperty> m_textureOverride;
std::vector<UniformBuffer> m_uniformBuffers;
const MaterialSettings& m_materialSettings;
};
}
#include <Nazara/Graphics/MaterialInstance.inl>
#endif // NAZARA_GRAPHICS_MATERIALINSTANCE_HPP

View File

@ -0,0 +1,216 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/MaterialInstance.hpp>
#include <type_traits>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline std::shared_ptr<MaterialInstance> MaterialInstance::Clone() const
{
return std::make_shared<MaterialInstance>(*this, CopyToken{});
}
inline void MaterialInstance::DisablePass(std::size_t passIndex)
{
EnablePass(passIndex, false);
}
inline void MaterialInstance::EnablePass(std::size_t passIndex, bool enable)
{
assert(passIndex < m_passes.size());
if (m_passes[passIndex].enabled != enable)
{
m_passes[passIndex].enabled = enable;
InvalidatePassPipeline(passIndex);
}
}
inline std::size_t MaterialInstance::FindTextureProperty(std::string_view propertyName) const
{
return m_materialSettings.FindTextureProperty(propertyName);
}
inline std::size_t MaterialInstance::FindValueProperty(std::string_view propertyName) const
{
return m_materialSettings.FindValueProperty(propertyName);
}
inline const std::shared_ptr<const Material>& MaterialInstance::GetParentMaterial() const
{
return m_parent;
}
inline MaterialPassFlags MaterialInstance::GetPassFlags(std::size_t passIndex) const
{
assert(passIndex < m_passes.size());
return m_passes[passIndex].flags;
}
inline const std::shared_ptr<Texture>* MaterialInstance::GetTextureProperty(std::string_view propertyName) const
{
std::size_t propertyIndex = FindTextureProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no texture property named " + std::string(propertyName));
return nullptr;
}
return &GetTextureProperty(propertyIndex);
}
inline const std::shared_ptr<Texture>& MaterialInstance::GetTextureProperty(std::size_t textureIndex) const
{
if (const std::shared_ptr<Texture>& textureOverride = GetTexturePropertyOverride(textureIndex))
return textureOverride;
else
return m_materialSettings.GetTextureProperty(textureIndex).defaultTexture;
}
inline const std::shared_ptr<Texture>& MaterialInstance::GetTexturePropertyOverride(std::size_t textureIndex) const
{
assert(textureIndex < m_textureOverride.size());
return m_textureOverride[textureIndex].texture;
}
inline const TextureSamplerInfo* MaterialInstance::GetTextureSamplerProperty(std::string_view propertyName) const
{
std::size_t propertyIndex = FindTextureProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no texture property named " + std::string(propertyName));
return nullptr;
}
return &GetTextureSamplerProperty(propertyIndex);
}
inline const TextureSamplerInfo& MaterialInstance::GetTextureSamplerProperty(std::size_t textureIndex) const
{
assert(textureIndex < m_textureOverride.size());
return m_textureOverride[textureIndex].samplerInfo;
}
inline const MaterialSettings::Value* MaterialInstance::GetValueProperty(std::string_view propertyName) const
{
std::size_t propertyIndex = FindValueProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no value property named " + std::string(propertyName));
return nullptr;
}
return &GetValueProperty(propertyIndex);
}
inline const MaterialSettings::Value& MaterialInstance::GetValueProperty(std::size_t valueIndex) const
{
if (const MaterialSettings::Value& valueOverride = GetValuePropertyOverride(valueIndex); !std::holds_alternative<MaterialPropertyNoValue>(valueOverride))
return valueOverride;
else
return m_materialSettings.GetValueProperty(valueIndex).defaultValue;
}
inline const MaterialSettings::Value& MaterialInstance::GetValuePropertyOverride(std::size_t valueIndex) const
{
assert(valueIndex < m_valueOverride.size());
return m_valueOverride[valueIndex];
}
inline bool MaterialInstance::HasPass(std::size_t passIndex) const
{
return passIndex < m_passes.size() && m_passes[passIndex].enabled;
}
inline void MaterialInstance::SetTextureProperty(std::string_view propertyName, std::shared_ptr<Texture> texture)
{
std::size_t propertyIndex = FindTextureProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no texture property named " + std::string(propertyName));
return;
}
return SetTextureProperty(propertyIndex, std::move(texture));
}
inline void MaterialInstance::SetTextureProperty(std::string_view propertyName, std::shared_ptr<Texture> texture, const TextureSamplerInfo& samplerInfo)
{
std::size_t propertyIndex = FindTextureProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no texture property named " + std::string(propertyName));
return;
}
return SetTextureProperty(propertyIndex, std::move(texture), samplerInfo);
}
inline void MaterialInstance::SetTextureSamplerProperty(std::string_view propertyName, const TextureSamplerInfo& samplerInfo)
{
std::size_t propertyIndex = FindTextureProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no texture property named " + std::string(propertyName));
return;
}
return SetTextureSamplerProperty(propertyIndex, samplerInfo);
}
inline void MaterialInstance::SetValueProperty(std::string_view propertyName, const MaterialSettings::Value& value)
{
std::size_t propertyIndex = FindValueProperty(propertyName);
if (propertyIndex == MaterialSettings::InvalidPropertyIndex)
{
NazaraError("material has no value property named " + std::string(propertyName));
return;
}
return SetValueProperty(propertyIndex, value);
}
inline void MaterialInstance::UpdatePassFlags(std::size_t passIndex, MaterialPassFlags materialFlags)
{
assert(passIndex < m_passes.size());
if (m_passes[passIndex].flags != materialFlags)
{
m_passes[passIndex].flags = materialFlags;
InvalidatePassPipeline(passIndex);
}
}
template<typename F>
void MaterialInstance::UpdatePassStates(std::size_t passIndex, F&& stateUpdater)
{
assert(passIndex < m_passes.size());
using Ret = std::invoke_result_t<F, RenderStates&>;
if constexpr (std::is_same_v<Ret, bool>)
{
if (!stateUpdater(static_cast<RenderStates&>(m_passes[passIndex].pipelineInfo)))
return;
}
else if constexpr (std::is_void_v<Ret>)
stateUpdater(static_cast<RenderStates&>(m_passes[passIndex].pipelineInfo));
else
static_assert(AlwaysFalse<Ret>(), "callback must either return a bool or nothing");
InvalidatePassPipeline(passIndex);
}
inline void MaterialInstance::InvalidatePassPipeline(std::size_t passIndex)
{
assert(passIndex < m_passes.size());
m_passes[passIndex].pipeline.reset();
OnMaterialInstancePipelineInvalidated(this, passIndex);
}
inline void MaterialInstance::InvalidateShaderBinding()
{
OnMaterialInstanceShaderBindingInvalidated(this);
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -10,10 +10,6 @@
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Core/Color.hpp> #include <Nazara/Core/Color.hpp>
#include <Nazara/Core/ObjectLibrary.hpp> #include <Nazara/Core/ObjectLibrary.hpp>
#include <Nazara/Core/Resource.hpp>
#include <Nazara/Core/ResourceLoader.hpp>
#include <Nazara/Core/ResourceManager.hpp>
#include <Nazara/Core/ResourceParameters.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/Enums.hpp> #include <Nazara/Graphics/Enums.hpp>
#include <Nazara/Graphics/MaterialPipeline.hpp> #include <Nazara/Graphics/MaterialPipeline.hpp>
@ -24,145 +20,19 @@
#include <Nazara/Utils/Signal.hpp> #include <Nazara/Utils/Signal.hpp>
#include <NZSL/Ast/ConstantValue.hpp> #include <NZSL/Ast/ConstantValue.hpp>
#include <array> #include <array>
#include <memory>
#include <string> #include <string>
#include <vector> #include <vector>
namespace Nz namespace Nz
{ {
class CommandBufferBuilder; struct MaterialPass
class RenderFrame;
class NAZARA_GRAPHICS_API MaterialPass
{ {
public: MaterialPassFlags flags;
MaterialPass(std::shared_ptr<const MaterialSettings> settings); RenderStates states;
MaterialPass(const MaterialPass&) = delete; std::unordered_map<UInt32, nzsl::Ast::ConstantSingleValue> options;
MaterialPass(MaterialPass&&) = delete; std::vector<std::shared_ptr<UberShader>> shaders;
inline ~MaterialPass();
inline void Configure(std::shared_ptr<MaterialPipeline> pipeline);
inline void Configure(const MaterialPipelineInfo& pipelineInfo);
inline void EnableBlending(bool blending);
inline void EnableColorWrite(bool colorWrite);
inline void EnableDepthBuffer(bool depthBuffer);
inline void EnableDepthClamp(bool depthClamp);
inline void EnableDepthWrite(bool depthWrite);
inline void EnableFaceCulling(bool faceCulling);
inline void EnableFlag(MaterialPassFlag flag, bool enable = true);
inline void EnableScissorTest(bool scissorTest);
inline void EnableStencilTest(bool stencilTest);
inline void EnsurePipelineUpdate() const;
void FillShaderBinding(std::vector<ShaderBinding::Binding>& bindings) const;
inline RendererComparison GetDepthCompareFunc() const;
inline BlendEquation GetBlendAlphaModeEquation() const;
inline BlendEquation GetBlendColorModeEquation() const;
inline BlendFunc GetBlendDstAlphaFunc() const;
inline BlendFunc GetBlendDstColorFunc() const;
inline BlendFunc GetBlendSrcAlphaFunc() const;
inline BlendFunc GetBlendSrcColorFunc() const;
inline FaceSide GetFaceCulling() const;
inline FaceFilling GetFaceFilling() const;
inline MaterialPassFlags GetFlags() const;
inline float GetLineWidth() const;
inline const nzsl::Ast::ConstantSingleValue& GetOptionValue(std::size_t optionIndex) const;
inline const std::shared_ptr<MaterialPipeline>& GetPipeline() const;
inline const MaterialPipelineInfo& GetPipelineInfo() const;
inline float GetPointSize() const;
inline PrimitiveMode GetPrimitiveMode() const;
inline const std::shared_ptr<const MaterialSettings>& GetSettings() const;
inline const std::shared_ptr<UberShader>& GetShader(nzsl::ShaderStageType shaderStage) const;
inline const std::shared_ptr<Texture>& GetTexture(std::size_t textureIndex) const;
inline const TextureSamplerInfo& GetTextureSampler(std::size_t textureIndex) const;
inline const std::shared_ptr<RenderBuffer>& GetUniformBuffer(std::size_t bufferIndex) const;
inline const std::vector<UInt8>& GetUniformBufferConstData(std::size_t bufferIndex) const;
inline std::vector<UInt8>& GetUniformBufferData(std::size_t bufferIndex);
inline bool HasTexture(std::size_t textureIndex) const;
inline bool IsBlendingEnabled() const;
inline bool IsColorWriteEnabled() const;
inline bool IsDepthBufferEnabled() const;
inline bool IsDepthClampEnabled() const;
inline bool IsDepthWriteEnabled() const;
inline bool IsFaceCullingEnabled() const;
inline bool IsFlagEnabled(MaterialPassFlag flag) const;
inline bool IsScissorTestEnabled() const;
inline bool IsStencilTestEnabled() const;
inline void SetDepthCompareFunc(RendererComparison depthFunc);
inline void SetBlendEquation(BlendEquation colorMode, BlendEquation alphaMode);
inline void SetBlendFunc(BlendFunc srcColor, BlendFunc dstColor, BlendFunc srcAlpha, BlendFunc dstAlpha);
inline void SetFaceCulling(FaceSide faceSide);
inline void SetFaceFilling(FaceFilling filling);
inline void SetLineWidth(float lineWidth);
inline void SetOptionValue(std::size_t optionIndex, nzsl::Ast::ConstantSingleValue value);
inline void SetPointSize(float pointSize);
inline void SetPrimitiveMode(PrimitiveMode mode);
inline void SetSharedUniformBuffer(std::size_t sharedUboIndex, std::shared_ptr<RenderBuffer> uniformBuffer);
inline void SetSharedUniformBuffer(std::size_t sharedUboIndex, std::shared_ptr<RenderBuffer> uniformBuffer, UInt64 offset, UInt64 size);
inline void SetTexture(std::size_t textureIndex, std::shared_ptr<Texture> texture);
inline void SetTextureSampler(std::size_t textureIndex, TextureSamplerInfo samplerInfo);
void Update(RenderFrame& renderFrame, CommandBufferBuilder& builder);
MaterialPass& operator=(const MaterialPass&) = delete;
MaterialPass& operator=(MaterialPass&&) = delete;
// Signals:
NazaraSignal(OnMaterialPassInvalidated, const MaterialPass* /*materialPass*/);
NazaraSignal(OnMaterialPassPipelineInvalidated, const MaterialPass* /*materialPass*/);
NazaraSignal(OnMaterialPassShaderBindingInvalidated, const MaterialPass* /*materialPass*/);
NazaraSignal(OnMaterialPassRelease, const MaterialPass* /*materialPass*/);
private:
inline void InvalidatePipeline();
inline void InvalidateShaderBinding();
inline void InvalidateTextureSampler(std::size_t textureIndex);
inline void InvalidateUniformData(std::size_t uniformBufferIndex);
void UpdatePipeline() const;
struct MaterialTexture
{
mutable std::shared_ptr<TextureSampler> sampler;
std::shared_ptr<Texture> texture;
TextureSamplerInfo samplerInfo;
};
struct ShaderEntry
{
NazaraSlot(UberShader, OnShaderUpdated, onShaderUpdated);
};
struct ShaderUniformBuffer
{
std::shared_ptr<RenderBuffer> buffer; //< kept for ownership
RenderBufferView bufferView;
};
struct UniformBuffer
{
std::shared_ptr<RenderBuffer> buffer;
std::vector<UInt8> data;
bool dataInvalidated = true;
};
std::array<nzsl::Ast::ConstantSingleValue, 64> m_optionValues;
std::shared_ptr<const MaterialSettings> m_settings;
std::vector<MaterialTexture> m_textures;
std::vector<ShaderEntry> m_shaders;
std::vector<ShaderUniformBuffer> m_sharedUniformBuffers;
std::vector<UniformBuffer> m_uniformBuffers;
mutable std::shared_ptr<MaterialPipeline> m_pipeline;
mutable MaterialPipelineInfo m_pipelineInfo;
MaterialPassFlags m_flags;
mutable bool m_pipelineUpdated;
}; };
} }
#include <Nazara/Graphics/MaterialPass.inl>
#endif // NAZARA_GRAPHICS_MATERIALPASS_HPP #endif // NAZARA_GRAPHICS_MATERIALPASS_HPP

View File

@ -1,683 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/MaterialPass.hpp>
#include <Nazara/Core/ErrorFlags.hpp>
#include <memory>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
/*!
* \brief Destructs the object and calls OnMaterialRelease
*
* \see OnMaterialRelease
*/
inline MaterialPass::~MaterialPass()
{
OnMaterialPassRelease(this);
}
/*!
* \brief Reset material pipeline state
*
* Sets the material pipeline
*
* \remark pipeline must be valid
*
* \see Configure
*/
inline void MaterialPass::Configure(std::shared_ptr<MaterialPipeline> pipeline)
{
NazaraAssert(pipeline, "Invalid material pipeline");
m_pipeline = std::move(pipeline);
m_pipelineInfo = m_pipeline->GetInfo();
m_pipelineUpdated = true;
}
/*!
* \brief Reset material pipeline state
*
* Sets the material pipeline using pipeline info
*
* \remark pipeline must be valid
*
* \see Configure
*/
inline void MaterialPass::Configure(const MaterialPipelineInfo& pipelineInfo)
{
m_pipelineInfo = pipelineInfo;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable blending for this material
*
* When enabled, all objects using this material will be rendered using blending, obeying the dstBlend and srcBlend parameters
* This is useful with translucent objects, but will reduces performance as it prevents some optimizations (as deferred rendering)
*
* \param blending Defines if this material will use blending
*
* \remark Invalidates the pipeline
*
* \see IsBlendingEnabled
* \see SetDstBlend
* \see SetSrcBlend
*/
inline void MaterialPass::EnableBlending(bool blending)
{
m_pipelineInfo.blending = blending;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable color writing for this material
*
* \param colorWrite Defines if this material will use color writing
*
* \remark Invalidates the pipeline
*
* \see IsColorWritingEnabled
*/
inline void MaterialPass::EnableColorWrite(bool colorWrite)
{
m_pipelineInfo.colorWrite = colorWrite;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable depth buffer for this material
*
* When enabled, all objects using this material will be rendered using a depth buffer, if the RenderTarget has one.
* This will enable Depth Test, preventing further fragments to render on top of closer ones.
*
* This parameter is required for depth writing.
*
* In order to enable depth writing without enabling depth test, set the depth comparison function to RendererComparison::Never
*
* \param depthBuffer Defines if this material will use depth buffer
*
* \remark Invalidates the pipeline
*
* \see EnableDepthWrite
* \see IsDepthBufferEnabled
* \see SetDepthFunc
*/
inline void MaterialPass::EnableDepthBuffer(bool depthBuffer)
{
m_pipelineInfo.depthBuffer = depthBuffer;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable depth clamp for this material
*
* When enabled, all fragments generated by this material will be clamped to znear or zfar
* instead of being clipped out when outside this range.
*
* This can be useful to prevent clipping near or far primitives.
*
* \param depthClamp Defines if this material will use depth clamping
*
* \remark Invalidates the pipeline
* \remark Depth clamping requires RenderDeviceFeatures::depthClamping to be true
*
* \see IsDepthClampEnabled
*/
inline void MaterialPass::EnableDepthClamp(bool depthClamp)
{
m_pipelineInfo.depthClamp = depthClamp;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable depth writing for this material
*
* When enabled, and if depth buffer is enabled and present, all fragments generated with this material will write
* to the depth buffer if they pass depth test.
*
* This is usually disabled with translucent objects, as depth test is wanted to prevent them from rendering on top of opaque objects but
* not depth writing (which could make other translucent fragments to fail depth test)
*
* \param depthBuffer Defines if this material will use depth write
*
* \remark Invalidates the pipeline
*
* \see EnableDepthBuffer
* \see IsDepthWriteEnabled
*/
inline void MaterialPass::EnableDepthWrite(bool depthWrite)
{
m_pipelineInfo.depthWrite = depthWrite;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable face culling for this material
*
* When enabled, the material prevents front and/or back faces from rendering.
* This is commonly used as an optimization to prevent processing of hidden faces by the rendering device.
*
* Use SetFaceCulling to control which side will be eliminated.
*
* \param faceCulling Defines if this material will use face culling
*
* \remark Invalidates the pipeline
*
* \see IsFaceCullingEnabled
* \see SetFaceCulling
*/
inline void MaterialPass::EnableFaceCulling(bool faceCulling)
{
m_pipelineInfo.faceCulling = faceCulling;
InvalidatePipeline();
}
inline void MaterialPass::EnableFlag(MaterialPassFlag flag, bool enable)
{
if (enable)
m_flags |= flag;
else
m_flags &= ~flag;
}
/*!
* \brief Enable/Disable scissor test for this material
*
* When enabled, the material prevents fragments out of the scissor box to be rendered.
* This can be useful with GUI, where widgets must not be rendered outside of their parent rendering area.
*
* \param scissorTest Defines if this material will use scissor test
*
* \remark Invalidates the pipeline
*
* \see IsScissorTestEnabled
*/
inline void MaterialPass::EnableScissorTest(bool scissorTest)
{
m_pipelineInfo.scissorTest = scissorTest;
InvalidatePipeline();
}
/*!
* \brief Enable/Disable stencil test for this material
*
* When enabled, all fragments must pass the stencil test to be rendered.
*
* \param scissorTest Defines if this material will use stencil test
*
* \remark Invalidates the pipeline
*
* \see IsStencilTestEnabled
*/
inline void MaterialPass::EnableStencilTest(bool stencilTest)
{
m_pipelineInfo.stencilTest = stencilTest;
InvalidatePipeline();
}
/*!
* \brief Ensures the pipeline gets updated
*
* When the pipeline gets invalidated, it's not updated until required (per example by calling GetPipeline).
* Using this function forces the pipeline update, making GetPipeline thread-safe as long as the pipeline does not get invalidated.
*
* \see GetPipeline
*/
inline void MaterialPass::EnsurePipelineUpdate() const
{
if (!m_pipelineUpdated)
UpdatePipeline();
}
/*!
* \brief Gets the function to compare depth
*
* \return Function comparing the depth of two materials
*
* \see EnableDepthTest
* \see SetAmbientColor
*/
inline RendererComparison MaterialPass::GetDepthCompareFunc() const
{
return m_pipelineInfo.depthCompare;
}
inline BlendEquation MaterialPass::GetBlendAlphaModeEquation() const
{
return m_pipelineInfo.blend.modeAlpha;
}
inline BlendEquation MaterialPass::GetBlendColorModeEquation() const
{
return m_pipelineInfo.blend.modeColor;
}
inline BlendFunc MaterialPass::GetBlendDstAlphaFunc() const
{
return m_pipelineInfo.blend.dstAlpha;
}
inline BlendFunc MaterialPass::GetBlendDstColorFunc() const
{
return m_pipelineInfo.blend.dstColor;
}
inline BlendFunc MaterialPass::GetBlendSrcAlphaFunc() const
{
return m_pipelineInfo.blend.srcAlpha;
}
inline BlendFunc MaterialPass::GetBlendSrcColorFunc() const
{
return m_pipelineInfo.blend.srcColor;
}
/*!
* \brief Gets the face culling
*
* \return Current face culling side
*
* \see SetFaceCulling
*/
inline FaceSide MaterialPass::GetFaceCulling() const
{
return m_pipelineInfo.cullingSide;
}
/*!
* \brief Gets the face filling
* \return Current face filling
*/
inline FaceFilling MaterialPass::GetFaceFilling() const
{
return m_pipelineInfo.faceFilling;
}
inline MaterialPassFlags MaterialPass::GetFlags() const
{
return m_flags;
}
/*!
* \brief Gets the line width of this material
* \return Line width
*/
inline float MaterialPass::GetLineWidth() const
{
return m_pipelineInfo.lineWidth;
}
inline const nzsl::Ast::ConstantSingleValue& MaterialPass::GetOptionValue(std::size_t optionIndex) const
{
assert(optionIndex < m_optionValues.size());
return m_optionValues[optionIndex];
}
/*!
* \brief Gets the render states
* \return Constant reference to the render states
*/
inline const std::shared_ptr<MaterialPipeline>& MaterialPass::GetPipeline() const
{
EnsurePipelineUpdate();
return m_pipeline;
}
/*!
* \brief Gets the pipeline informations
* \return Constant reference to the pipeline info
*/
inline const MaterialPipelineInfo& MaterialPass::GetPipelineInfo() const
{
return m_pipelineInfo;
}
/*!
* \brief Gets the point size of this material
* \return Point size
*/
inline float MaterialPass::GetPointSize() const
{
return m_pipelineInfo.pointSize;
}
inline PrimitiveMode MaterialPass::GetPrimitiveMode() const
{
return m_pipelineInfo.primitiveMode;
}
inline const std::shared_ptr<const MaterialSettings>& MaterialPass::GetSettings() const
{
return m_settings;
}
/*!
* \brief Gets the über-shader used by this material
* \return Constant pointer to the über-shader used
*/
inline const std::shared_ptr<UberShader>& MaterialPass::GetShader(nzsl::ShaderStageType shaderStage) const
{
return m_pipelineInfo.shaders[UnderlyingCast(shaderStage)].uberShader;
}
inline const std::shared_ptr<Texture>& MaterialPass::GetTexture(std::size_t textureIndex) const
{
NazaraAssert(textureIndex < m_textures.size(), "Invalid texture index");
return m_textures[textureIndex].texture;
}
inline const TextureSamplerInfo& MaterialPass::GetTextureSampler(std::size_t textureIndex) const
{
NazaraAssert(textureIndex < m_textures.size(), "Invalid texture index");
return m_textures[textureIndex].samplerInfo;
}
inline const std::shared_ptr<RenderBuffer>& MaterialPass::GetUniformBuffer(std::size_t bufferIndex) const
{
NazaraAssert(bufferIndex < m_uniformBuffers.size(), "Invalid uniform buffer index");
return m_uniformBuffers[bufferIndex].buffer;
}
inline const std::vector<UInt8>& MaterialPass::GetUniformBufferConstData(std::size_t bufferIndex) const
{
NazaraAssert(bufferIndex < m_uniformBuffers.size(), "Invalid uniform buffer index");
return m_uniformBuffers[bufferIndex].data;
}
inline std::vector<UInt8>& MaterialPass::GetUniformBufferData(std::size_t bufferIndex)
{
NazaraAssert(bufferIndex < m_uniformBuffers.size(), "Invalid uniform buffer index");
UniformBuffer& uboEntry = m_uniformBuffers[bufferIndex];
InvalidateUniformData(bufferIndex);
return uboEntry.data;
}
inline bool MaterialPass::HasTexture(std::size_t textureIndex) const
{
return GetTexture(textureIndex) != nullptr;
}
/*!
* \brief Checks whether this material has blending enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsBlendingEnabled() const
{
return m_pipelineInfo.blending;
}
/*!
* \brief Checks whether this material has color write enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsColorWriteEnabled() const
{
return m_pipelineInfo.colorWrite;
}
/*!
* \brief Checks whether this material has depth buffer enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsDepthBufferEnabled() const
{
return m_pipelineInfo.depthBuffer;
}
/*!
* \brief Checks whether this material has depth clamping enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsDepthClampEnabled() const
{
return m_pipelineInfo.depthClamp;
}
/*!
* \brief Checks whether this material has depth writing enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsDepthWriteEnabled() const
{
return m_pipelineInfo.depthWrite;
}
/*!
* \brief Checks whether this material has face culling enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsFaceCullingEnabled() const
{
return m_pipelineInfo.faceCulling;
}
inline bool MaterialPass::IsFlagEnabled(MaterialPassFlag flag) const
{
return m_flags.Test(flag);
}
/*!
* \brief Checks whether this material has scissor test enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsScissorTestEnabled() const
{
return m_pipelineInfo.scissorTest;
}
/*!
* \brief Checks whether this material has stencil test enabled
* \return true If it is the case
*/
inline bool MaterialPass::IsStencilTestEnabled() const
{
return m_pipelineInfo.stencilTest;
}
/*!
* \brief Sets the depth functor
*
* \param depthFunc
*
* \remark Invalidates the pipeline
*/
inline void MaterialPass::SetDepthCompareFunc(RendererComparison depthFunc)
{
m_pipelineInfo.depthCompare = depthFunc;
InvalidatePipeline();
}
inline void MaterialPass::SetBlendEquation(BlendEquation colorMode, BlendEquation alphaMode)
{
m_pipelineInfo.blend.modeAlpha = alphaMode;
m_pipelineInfo.blend.modeColor = colorMode;
InvalidatePipeline();
}
inline void MaterialPass::SetBlendFunc(BlendFunc srcColor, BlendFunc dstColor, BlendFunc srcAlpha, BlendFunc dstAlpha)
{
m_pipelineInfo.blend.dstAlpha = dstAlpha;
m_pipelineInfo.blend.dstColor = dstColor;
m_pipelineInfo.blend.srcAlpha = srcAlpha;
m_pipelineInfo.blend.srcColor = srcColor;
InvalidatePipeline();
}
/*!
* \brief Sets the face culling
*
* \param faceSide Face to cull
*
* \remark Invalidates the pipeline
*/
inline void MaterialPass::SetFaceCulling(FaceSide faceSide)
{
m_pipelineInfo.cullingSide = faceSide;
InvalidatePipeline();
}
/*!
* \brief Sets the face filling
*
* \param filling Face to fill
*
* \remark Invalidates the pipeline
*/
inline void MaterialPass::SetFaceFilling(FaceFilling filling)
{
m_pipelineInfo.faceFilling = filling;
InvalidatePipeline();
}
/*!
* \brief Sets the line width for this material
*
* This parameter is used when rendering lines, to define the width (in pixels) the line will take on the framebuffer
*
* \param lineWidth Width of the line
*
* \remark Invalidates the pipeline
*
* \see GetLineWidth
*/
inline void MaterialPass::SetLineWidth(float lineWidth)
{
m_pipelineInfo.lineWidth = lineWidth;
InvalidatePipeline();
}
inline void MaterialPass::SetOptionValue(std::size_t optionIndex, nzsl::Ast::ConstantSingleValue value)
{
assert(optionIndex < m_optionValues.size());
if (m_optionValues[optionIndex] != value)
{
m_optionValues[optionIndex] = std::move(value);
InvalidatePipeline();
}
}
/*!
* \brief Sets the point size for this material
*
* This parameter is used when rendering points, to define the size (in pixels) the point will take on the framebuffer
*
* \param pointSize Size of the point
*
* \remark Invalidates the pipeline
*
* \see GetPointSize
*/
inline void MaterialPass::SetPointSize(float pointSize)
{
m_pipelineInfo.pointSize = pointSize;
InvalidatePipeline();
}
inline void MaterialPass::SetPrimitiveMode(PrimitiveMode mode)
{
m_pipelineInfo.primitiveMode = mode;
InvalidatePipeline();
}
inline void MaterialPass::SetSharedUniformBuffer(std::size_t sharedUboIndex, std::shared_ptr<RenderBuffer> uniformBuffer)
{
if (uniformBuffer)
{
UInt64 size = uniformBuffer->GetSize();
return SetSharedUniformBuffer(sharedUboIndex, std::move(uniformBuffer), 0, size);
}
else
return SetSharedUniformBuffer(sharedUboIndex, std::move(uniformBuffer), 0, 0);
}
inline void MaterialPass::SetSharedUniformBuffer(std::size_t sharedUboIndex, std::shared_ptr<RenderBuffer> uniformBuffer, UInt64 offset, UInt64 size)
{
NazaraAssert(sharedUboIndex < m_sharedUniformBuffers.size(), "Invalid shared uniform buffer index");
RenderBufferView bufferView(uniformBuffer.get(), offset, size);
if (m_sharedUniformBuffers[sharedUboIndex].bufferView != bufferView)
{
m_sharedUniformBuffers[sharedUboIndex].bufferView = bufferView;
m_sharedUniformBuffers[sharedUboIndex].buffer = std::move(uniformBuffer);
InvalidateShaderBinding();
}
}
inline void MaterialPass::SetTexture(std::size_t textureIndex, std::shared_ptr<Texture> texture)
{
NazaraAssert(textureIndex < m_textures.size(), "Invalid texture index");
if (m_textures[textureIndex].texture != texture)
{
m_textures[textureIndex].texture = std::move(texture);
InvalidateShaderBinding();
}
}
inline void MaterialPass::SetTextureSampler(std::size_t textureIndex, TextureSamplerInfo samplerInfo)
{
NazaraAssert(textureIndex < m_textures.size(), "Invalid texture index");
if (m_textures[textureIndex].samplerInfo != samplerInfo)
{
m_textures[textureIndex].samplerInfo = std::move(samplerInfo);
InvalidateTextureSampler(textureIndex);
}
}
inline void MaterialPass::InvalidatePipeline()
{
m_pipelineUpdated = false;
OnMaterialPassPipelineInvalidated(this);
}
inline void MaterialPass::InvalidateShaderBinding()
{
OnMaterialPassShaderBindingInvalidated(this);
}
inline void MaterialPass::InvalidateTextureSampler(std::size_t textureIndex)
{
assert(textureIndex < m_textures.size());
m_textures[textureIndex].sampler.reset();
InvalidateShaderBinding();
}
inline void MaterialPass::InvalidateUniformData(std::size_t uniformBufferIndex)
{
assert(uniformBufferIndex < m_uniformBuffers.size());
UniformBuffer& uboEntry = m_uniformBuffers[uniformBufferIndex];
uboEntry.dataInvalidated = true;
OnMaterialPassInvalidated(this);
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -8,6 +8,8 @@
#define NAZARA_GRAPHICS_MATERIALPASSREGISTRY_HPP #define NAZARA_GRAPHICS_MATERIALPASSREGISTRY_HPP
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Utils/Algorithm.hpp>
#include <list>
#include <string> #include <string>
#include <unordered_map> #include <unordered_map>
@ -21,7 +23,7 @@ namespace Nz
MaterialPassRegistry(MaterialPassRegistry&&) = default; MaterialPassRegistry(MaterialPassRegistry&&) = default;
~MaterialPassRegistry() = default; ~MaterialPassRegistry() = default;
inline std::size_t GetPassIndex(const std::string& passName) const; inline std::size_t GetPassIndex(std::string_view passName) const;
inline std::size_t RegisterPass(std::string passName); inline std::size_t RegisterPass(std::string passName);
@ -29,7 +31,8 @@ namespace Nz
MaterialPassRegistry& operator=(MaterialPassRegistry&&) = default; MaterialPassRegistry& operator=(MaterialPassRegistry&&) = default;
private: private:
std::unordered_map<std::string, std::size_t> m_passIndex; std::list<std::string> m_passNames; //< in order to allow std::string_view as a key in C++17 (keep std::string stable as well because of SSO)
std::unordered_map<std::string_view, std::size_t> m_passIndex;
}; };
} }

View File

@ -8,11 +8,11 @@
namespace Nz namespace Nz
{ {
std::size_t MaterialPassRegistry::GetPassIndex(const std::string& passName) const std::size_t MaterialPassRegistry::GetPassIndex(std::string_view passName) const
{ {
auto it = m_passIndex.find(passName); auto it = m_passIndex.find(passName);
if (it == m_passIndex.end()) if (it == m_passIndex.end())
throw std::runtime_error("pass " + passName + " must be registered before being used"); throw std::runtime_error("pass " + std::string(passName) + " must be registered before being used");
return it->second; return it->second;
} }
@ -22,8 +22,10 @@ namespace Nz
if (m_passIndex.find(passName) != m_passIndex.end()) if (m_passIndex.find(passName) != m_passIndex.end())
throw std::runtime_error("pass " + passName + " is already registered"); throw std::runtime_error("pass " + passName + " is already registered");
m_passNames.push_back(std::move(passName));
std::size_t passIndex = m_passIndex.size(); std::size_t passIndex = m_passIndex.size();
m_passIndex.emplace(std::move(passName), passIndex); m_passIndex.emplace(m_passNames.back(), passIndex);
return passIndex; return passIndex;
} }

View File

@ -10,7 +10,7 @@
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/Enums.hpp> #include <Nazara/Graphics/Enums.hpp>
#include <Nazara/Graphics/MaterialSettings.hpp> #include <Nazara/Graphics/UberShader.hpp>
#include <Nazara/Renderer/RenderPipeline.hpp> #include <Nazara/Renderer/RenderPipeline.hpp>
#include <NZSL/Ast/ConstantValue.hpp> #include <NZSL/Ast/ConstantValue.hpp>
#include <array> #include <array>
@ -33,10 +33,9 @@ namespace Nz
std::shared_ptr<UberShader> uberShader; std::shared_ptr<UberShader> uberShader;
}; };
std::array<Option, 32> optionValues; std::shared_ptr<RenderPipelineLayout> pipelineLayout;
std::size_t optionCount = 0; std::vector<Option> optionValues; //< TODO: FixedVector
std::vector<Shader> shaders; std::vector<Shader> shaders; //< TODO: FixedVector
std::shared_ptr<const MaterialSettings> settings;
}; };
inline bool operator==(const MaterialPipelineInfo& lhs, const MaterialPipelineInfo& rhs); inline bool operator==(const MaterialPipelineInfo& lhs, const MaterialPipelineInfo& rhs);

View File

@ -40,16 +40,13 @@ namespace Nz
#define NazaraPipelineMember(field) if (lhs.field != rhs.field) return false #define NazaraPipelineMember(field) if (lhs.field != rhs.field) return false
NazaraPipelineMember(settings);
NazaraPipelineMember(optionCount);
for (std::size_t i = 0; i < lhs.shaders.size(); ++i) for (std::size_t i = 0; i < lhs.shaders.size(); ++i)
{ {
if (lhs.shaders[i].uberShader != rhs.shaders[i].uberShader) if (lhs.shaders[i].uberShader != rhs.shaders[i].uberShader)
return false; return false;
} }
for (std::size_t i = 0; i < lhs.optionCount; ++i) for (std::size_t i = 0; i < lhs.optionValues.size(); ++i)
{ {
if (lhs.optionValues[i].hash != rhs.optionValues[i].hash) if (lhs.optionValues[i].hash != rhs.optionValues[i].hash)
return false; return false;
@ -86,9 +83,7 @@ namespace std
#define NazaraPipelineMember(member) Nz::HashCombine(seed, pipelineInfo.member) #define NazaraPipelineMember(member) Nz::HashCombine(seed, pipelineInfo.member)
#define NazaraPipelineBoolMember(member) parameterHash |= ((pipelineInfo.member) ? 1U : 0U) << (parameterIndex++) #define NazaraPipelineBoolMember(member) parameterHash |= ((pipelineInfo.member) ? 1U : 0U) << (parameterIndex++)
NazaraPipelineMember(settings.get()); //< Hash pointer for (std::size_t i = 0; i < pipelineInfo.optionValues.size(); ++i)
for (std::size_t i = 0; i < pipelineInfo.optionCount; ++i)
{ {
Nz::HashCombine(seed, pipelineInfo.optionValues[i].hash); Nz::HashCombine(seed, pipelineInfo.optionValues[i].hash);
Nz::HashCombine(seed, pipelineInfo.optionValues[i].value); Nz::HashCombine(seed, pipelineInfo.optionValues[i].value);

View File

@ -8,110 +8,100 @@
#define NAZARA_GRAPHICS_MATERIALSETTINGS_HPP #define NAZARA_GRAPHICS_MATERIALSETTINGS_HPP
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Core/Color.hpp>
#include <Nazara/Graphics/Enums.hpp> #include <Nazara/Graphics/Enums.hpp>
#include <Nazara/Graphics/UberShader.hpp> #include <Nazara/Graphics/MaterialPass.hpp>
#include <Nazara/Renderer/RenderPipelineLayout.hpp> #include <Nazara/Graphics/PropertyHandler/PropertyHandler.hpp>
#include <Nazara/Renderer/ShaderModule.hpp> #include <Nazara/Math/Vector2.hpp>
#include <Nazara/Utility/Enums.hpp> #include <Nazara/Math/Vector3.hpp>
#include <array> #include <Nazara/Math/Vector4.hpp>
#include <Nazara/Renderer/Texture.hpp>
#include <Nazara/Utils/TypeList.hpp>
#include <limits> #include <limits>
#include <optional>
#include <string> #include <string>
#include <variant>
#include <vector> #include <vector>
namespace Nz namespace Nz
{ {
class MaterialSettings template<typename T> struct TypeToMaterialPropertyType;
template<typename T> constexpr MaterialPropertyType TypeToMaterialPropertyType_v = TypeToMaterialPropertyType<T>::PropertyType;
template<MaterialPropertyType P> struct MaterialPropertyTypeInfo;
struct MaterialPropertyNoValue {};
using MaterialPropertyTypeList = TypeList<
MaterialPropertyNoValue,
Color,
bool, Vector2<bool>, Vector3<bool>, Vector4<bool>,
float, Vector2<float>, Vector3<float>, Vector4<float>,
Int32, Vector2<Int32>, Vector3<Int32>, Vector4<Int32>,
UInt32, Vector2<UInt32>, Vector3<UInt32>, Vector4<UInt32>
>;
class NAZARA_GRAPHICS_API MaterialSettings
{ {
public: public:
struct Builder; struct TextureProperty;
struct Option; struct ValueProperty;
struct SharedUniformBlock;
struct Texture;
struct UniformBlock;
using PredefinedBinding = std::array<std::size_t, PredefinedShaderBindingCount>;
inline MaterialSettings(); using Value = TypeListInstantiate<MaterialPropertyTypeList, std::variant>;
inline MaterialSettings(Builder builder);
MaterialSettings(const MaterialSettings&) = default; MaterialSettings() = default;
MaterialSettings(MaterialSettings&&) = delete; MaterialSettings(const MaterialSettings&) = delete;
MaterialSettings(MaterialSettings&&) noexcept = default;
~MaterialSettings() = default; ~MaterialSettings() = default;
inline const Builder& GetBuilderData() const; void AddPass(std::string_view passName, MaterialPass materialPass);
inline const std::vector<Option>& GetOptions() const; inline void AddPass(std::size_t passIndex, MaterialPass materialPass);
inline std::size_t GetOptionIndex(const std::string_view& name) const; inline void AddPropertyHandler(std::unique_ptr<PropertyHandler> propertyHandler);
inline std::size_t GetPredefinedBinding(PredefinedShaderBinding shaderBinding) const; inline void AddTextureProperty(std::string propertyName, ImageType propertyType);
inline const std::shared_ptr<RenderPipelineLayout>& GetRenderPipelineLayout() const; inline void AddTextureProperty(std::string propertyName, ImageType propertyType, std::shared_ptr<Texture> defaultTexture);
inline const std::shared_ptr<UberShader>& GetShader(nzsl::ShaderStageType stage) const; inline void AddTextureProperty(std::string propertyName, ImageType propertyType, std::shared_ptr<Texture> defaultTexture, const TextureSamplerInfo& defaultSamplerInfo);
inline const std::vector<std::shared_ptr<UberShader>>& GetShaders() const; inline void AddValueProperty(std::string propertyName, MaterialPropertyType propertyType, Value defaultValue);
inline const std::vector<SharedUniformBlock>& GetSharedUniformBlocks() const; template<typename T> void AddValueProperty(std::string propertyName);
inline std::size_t GetSharedUniformBlockIndex(const std::string_view& name) const; template<typename T, typename U> void AddValueProperty(std::string propertyName, U&& defaultValue);
inline std::size_t GetSharedUniformBlockVariableOffset(std::size_t uniformBlockIndex, const std::string_view& name) const;
inline const std::vector<Texture>& GetTextures() const; inline std::size_t FindTextureProperty(std::string_view propertyName) const;
inline std::size_t GetTextureIndex(const std::string_view& name) const; inline std::size_t FindValueProperty(std::string_view propertyName) const;
inline const std::vector<UniformBlock>& GetUniformBlocks() const;
inline std::size_t GetUniformBlockIndex(const std::string_view& name) const; const MaterialPass* GetPass(std::string_view passName) const;
inline std::size_t GetUniformBlockVariableOffset(std::size_t uniformBlockIndex, const std::string_view& name) const; inline const MaterialPass* GetPass(std::size_t passIndex) const;
inline const std::vector<std::optional<MaterialPass>>& GetPasses() const;
inline const std::vector<std::unique_ptr<PropertyHandler>>& GetPropertyHandlers() const;
inline const TextureProperty& GetTextureProperty(std::size_t texturePropertyIndex) const;
inline std::size_t GetTexturePropertyCount() const;
inline const ValueProperty& GetValueProperty(std::size_t valuePropertyIndex) const;
inline std::size_t GetValuePropertyCount() const;
MaterialSettings& operator=(const MaterialSettings&) = delete; MaterialSettings& operator=(const MaterialSettings&) = delete;
MaterialSettings& operator=(MaterialSettings&&) = delete; MaterialSettings& operator=(MaterialSettings&&) = default;
static constexpr std::size_t InvalidIndex = std::numeric_limits<std::size_t>::max(); struct TextureProperty
static inline void BuildOption(std::vector<Option>& options, std::string optionName, const std::string& shaderOptionName);
struct Builder
{ {
inline Builder(); std::shared_ptr<Texture> defaultTexture;
std::vector<std::shared_ptr<UberShader>> shaders;
std::vector<Option> options;
std::vector<Texture> textures;
std::vector<UniformBlock> uniformBlocks;
std::vector<SharedUniformBlock> sharedUniformBlocks;
PredefinedBinding predefinedBindings;
};
struct Option
{
std::string name;
UInt32 hash;
};
struct UniformVariable
{
std::string name;
std::size_t offset;
};
struct SharedUniformBlock
{
UInt32 bindingIndex;
std::string name;
std::vector<UniformVariable> uniforms;
nzsl::ShaderStageTypeFlags shaderStages = nzsl::ShaderStageType_All;
};
struct Texture
{
UInt32 bindingIndex;
std::string name; std::string name;
ImageType type; ImageType type;
nzsl::ShaderStageTypeFlags shaderStages = nzsl::ShaderStageType_All; TextureSamplerInfo defaultSamplerInfo;
}; };
struct UniformBlock struct ValueProperty
{ {
UInt32 bindingIndex; Value defaultValue;
std::string name; std::string name;
std::size_t blockSize; MaterialPropertyType type;
std::vector<UniformVariable> uniforms;
std::vector<UInt8> defaultValues;
nzsl::ShaderStageTypeFlags shaderStages = nzsl::ShaderStageType_All;
}; };
static constexpr std::size_t InvalidPropertyIndex = std::numeric_limits<std::size_t>::max();
private: private:
std::shared_ptr<RenderPipelineLayout> m_pipelineLayout; std::vector<std::unique_ptr<PropertyHandler>> m_propertyHandlers;
Builder m_data; std::vector<std::optional<MaterialPass>> m_materialPasses;
std::vector<TextureProperty> m_textureProperties;
std::vector<ValueProperty> m_valueProperties;
}; };
} }

View File

@ -3,186 +3,327 @@
// For conditions of distribution and use, see copyright notice in Config.hpp // For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/MaterialSettings.hpp> #include <Nazara/Graphics/MaterialSettings.hpp>
#include <Nazara/Core/Algorithm.hpp> #include <Nazara/Utils/Algorithm.hpp>
#include <Nazara/Graphics/Graphics.hpp> #include <stdexcept>
#include <cassert>
#include <Nazara/Graphics/Debug.hpp> #include <Nazara/Graphics/Debug.hpp>
namespace Nz namespace Nz
{ {
inline MaterialSettings::MaterialSettings() : template<typename T> class Vector2;
MaterialSettings(Builder{}) template<typename T> class Vector3;
template<typename T> class Vector4;
template<typename T>
struct TypeToMaterialPropertyType
{ {
static_assert(AlwaysFalse<T>(), "T is not a valid type for material property");
};
template<> struct TypeToMaterialPropertyType<bool> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Bool; };
template<> struct TypeToMaterialPropertyType<Vector2<bool>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Bool2; };
template<> struct TypeToMaterialPropertyType<Vector3<bool>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Bool3; };
template<> struct TypeToMaterialPropertyType<Vector4<bool>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Bool4; };
template<> struct TypeToMaterialPropertyType<Color> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Color; };
template<> struct TypeToMaterialPropertyType<float> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Float; };
template<> struct TypeToMaterialPropertyType<Vector2<float>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Float2; };
template<> struct TypeToMaterialPropertyType<Vector3<float>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Float3; };
template<> struct TypeToMaterialPropertyType<Vector4<float>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Float4; };
template<> struct TypeToMaterialPropertyType<Int32> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Int; };
template<> struct TypeToMaterialPropertyType<Vector2<Int32>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Int2; };
template<> struct TypeToMaterialPropertyType<Vector3<Int32>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Int3; };
template<> struct TypeToMaterialPropertyType<Vector4<Int32>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::Int4; };
template<> struct TypeToMaterialPropertyType<UInt32> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::UInt; };
template<> struct TypeToMaterialPropertyType<Vector2<UInt32>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::UInt2; };
template<> struct TypeToMaterialPropertyType<Vector3<UInt32>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::UInt3; };
template<> struct TypeToMaterialPropertyType<Vector4<UInt32>> { static constexpr MaterialPropertyType PropertyType = MaterialPropertyType::UInt4; };
template<MaterialPropertyType P>
struct MaterialPropertyTypeInfo
{
};
template<typename T>
struct MaterialPropertyTypeInfoPrimitive
{
using Type = T;
using BufferType = T;
using OptionType = T;
static Type DecodeFromBuffer(BufferType value) { return value; }
static Type DecodeFromOption(OptionType value) { return value; }
static BufferType EncodeToBuffer(Type value) { return value; }
static OptionType EncodeToOption(Type value) { return value; }
};
template<typename T, std::size_t N>
struct MaterialPropertyTypeInfoVector;
template<typename T>
struct MaterialPropertyTypeInfoVector<T, 2>
{
using Type = Vector2<T>;
using BufferType = nzsl::Vector2<T>;
using OptionType = nzsl::Vector2<T>;
static Type DecodeFromBuffer(BufferType value) { return { value.x(), value.y() }; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.x, value.y }; }
static OptionType EncodeToOption(Type value) { return OptionType{ value.x, value.y }; }
};
template<typename T>
struct MaterialPropertyTypeInfoVector<T, 3>
{
using Type = Vector3<T>;
using BufferType = nzsl::Vector3<T>;
using OptionType = nzsl::Vector3<T>;
static Type DecodeFromBuffer(BufferType value) { return { value.x(), value.y(), value.z() }; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y(), value.z() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.x, value.y, value.z }; }
static OptionType EncodeToOption(Type value) { return OptionType{ value.x, value.y, value.z }; }
};
template<typename T>
struct MaterialPropertyTypeInfoVector<T, 4>
{
using Type = Vector4<T>;
using BufferType = nzsl::Vector4<T>;
using OptionType = nzsl::Vector4<T>;
static Type DecodeFromBuffer(BufferType value) { return { value.x(), value.y(), value.z(), value.w() }; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y(), value.z(), value.w() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.x, value.y, value.z, value.w }; }
static OptionType EncodeToOption(Type value) { return OptionType{ value.x, value.y, value.z, value.w }; }
};
template<>
struct MaterialPropertyTypeInfo<MaterialPropertyType::Bool>
{
using Type = bool;
using BufferType = UInt32;
using OptionType = bool;
static Type DecodeFromBuffer(BufferType value) { return value != 0; }
static Type DecodeFromOption(OptionType value) { return value; }
static BufferType EncodeToBuffer(Type value) { return value; }
static OptionType EncodeToOption(Type value) { return value; }
};
template<>
struct MaterialPropertyTypeInfo<MaterialPropertyType::Bool2>
{
using Type = Vector2<bool>;
using BufferType = nzsl::Vector2u32;
using OptionType = nzsl::Vector2<bool>;
static Type DecodeFromBuffer(BufferType value) { return { value.x() != 0, value.y() != 0 }; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.x, value.y }; }
static OptionType EncodeToOption(Type value) { return OptionType{ value.x, value.y }; }
};
template<>
struct MaterialPropertyTypeInfo<MaterialPropertyType::Bool3>
{
using Type = Vector3<bool>;
using BufferType = nzsl::Vector3u32;
using OptionType = nzsl::Vector3<bool>;
static Type DecodeFromBuffer(BufferType value) { return { value.x() != 0, value.y() != 0, value.z() != 0 }; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y(), value.z() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.x, value.y, value.z }; }
static OptionType EncodeToOption(Type value) { return OptionType{ value.x, value.y, value.z }; }
};
template<>
struct MaterialPropertyTypeInfo<MaterialPropertyType::Bool4>
{
using Type = Vector4<bool>;
using BufferType = nzsl::Vector4u32;
using OptionType = nzsl::Vector4<bool>;
static Type DecodeFromBuffer(BufferType value) { return { value.x() != 0, value.y() != 0, value.z() != 0, value.w() != 0}; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y(), value.z(), value.w() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.x, value.y, value.z, value.w }; }
static OptionType EncodeToOption(Type value) { return OptionType{ value.x, value.y, value.z, value.w }; }
};
template<>
struct MaterialPropertyTypeInfo<MaterialPropertyType::Color>
{
using Type = Color;
using BufferType = nzsl::Vector4f32;
using OptionType = nzsl::Vector4f32;
static Type DecodeFromBuffer(BufferType value) { return { value.x(), value.y(), value.z(), value.w() }; }
static Type DecodeFromOption(OptionType value) { return { value.x(), value.y(), value.z(), value.w() }; }
static BufferType EncodeToBuffer(Type value) { return BufferType{ value.r, value.g, value.b, value.a }; }
static OptionType EncodeToOption(Type value) { return BufferType{ value.r, value.g, value.b, value.a }; }
};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Float> : MaterialPropertyTypeInfoPrimitive<float> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Float2> : MaterialPropertyTypeInfoVector<float, 2> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Float3> : MaterialPropertyTypeInfoVector<float, 3> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Float4> : MaterialPropertyTypeInfoVector<float, 4> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Int> : MaterialPropertyTypeInfoPrimitive<Int32> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Int2> : MaterialPropertyTypeInfoVector<Int32, 2> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Int3> : MaterialPropertyTypeInfoVector<Int32, 3> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::Int4> : MaterialPropertyTypeInfoVector<Int32, 4> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::UInt> : MaterialPropertyTypeInfoPrimitive<UInt32> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::UInt2> : MaterialPropertyTypeInfoVector<UInt32, 2> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::UInt3> : MaterialPropertyTypeInfoVector<UInt32, 3> {};
template<> struct MaterialPropertyTypeInfo<MaterialPropertyType::UInt4> : MaterialPropertyTypeInfoVector<UInt32, 4> {};
inline void MaterialSettings::AddPass(std::size_t passIndex, MaterialPass materialPass)
{
if (passIndex >= m_materialPasses.size())
m_materialPasses.resize(passIndex + 1);
m_materialPasses[passIndex] = std::move(materialPass);
} }
inline MaterialSettings::MaterialSettings(Builder data) : inline void MaterialSettings::AddPropertyHandler(std::unique_ptr<PropertyHandler> propertyHandler)
m_data(std::move(data))
{ {
RenderPipelineLayoutInfo info; m_propertyHandlers.emplace_back(std::move(propertyHandler));
for (const Texture& textureInfo : m_data.textures)
{
info.bindings.push_back({
0,
textureInfo.bindingIndex,
ShaderBindingType::Texture,
textureInfo.shaderStages
});
}
for (const UniformBlock& ubo : m_data.uniformBlocks)
{
info.bindings.push_back({
0,
ubo.bindingIndex,
ShaderBindingType::UniformBuffer,
ubo.shaderStages
});
}
for (const SharedUniformBlock& ubo : m_data.sharedUniformBlocks)
{
info.bindings.push_back({
0,
ubo.bindingIndex,
ShaderBindingType::UniformBuffer,
ubo.shaderStages
});
}
m_pipelineLayout = Graphics::Instance()->GetRenderDevice()->InstantiateRenderPipelineLayout(std::move(info));
} }
inline auto MaterialSettings::GetBuilderData() const -> const Builder& inline void MaterialSettings::AddTextureProperty(std::string propertyName, ImageType propertyType)
{ {
return m_data; auto& textureProperty = m_textureProperties.emplace_back();
textureProperty.name = std::move(propertyName);
textureProperty.type = propertyType;
} }
inline auto MaterialSettings::GetOptions() const -> const std::vector<Option>& inline void MaterialSettings::AddTextureProperty(std::string propertyName, ImageType propertyType, std::shared_ptr<Texture> defaultTexture)
{ {
return m_data.options; if (defaultTexture && defaultTexture->GetType() != propertyType)
throw std::runtime_error("default texture type doesn't match property image type");
auto& textureProperty = m_textureProperties.emplace_back();
textureProperty.name = std::move(propertyName);
textureProperty.type = propertyType;
textureProperty.defaultTexture = std::move(defaultTexture);
} }
inline std::size_t MaterialSettings::GetOptionIndex(const std::string_view& name) const inline void MaterialSettings::AddTextureProperty(std::string propertyName, ImageType propertyType, std::shared_ptr<Texture> defaultTexture, const TextureSamplerInfo& defaultSamplerInfo)
{ {
for (std::size_t i = 0; i < m_data.options.size(); ++i) if (defaultTexture && defaultTexture->GetType() != propertyType)
throw std::runtime_error("default texture type doesn't match property image type");
auto& textureProperty = m_textureProperties.emplace_back();
textureProperty.name = std::move(propertyName);
textureProperty.type = propertyType;
textureProperty.defaultTexture = std::move(defaultTexture);
textureProperty.defaultSamplerInfo = defaultSamplerInfo;
}
inline void MaterialSettings::AddValueProperty(std::string propertyName, MaterialPropertyType propertyType, Value defaultValue)
{
std::visit([&](auto&& arg)
{ {
if (m_data.options[i].name == name) using T = std::decay_t<decltype(arg)>;
if constexpr (!std::is_same_v<T, MaterialPropertyNoValue>)
{
constexpr MaterialPropertyType valueType = TypeToMaterialPropertyType_v<T>;
if (propertyType != valueType)
throw std::runtime_error("default value type doesn't match property type");
}
else
throw std::runtime_error("value properties must have a default value");
}, defaultValue);
auto& valueProperty = m_valueProperties.emplace_back();
valueProperty.name = std::move(propertyName);
valueProperty.type = propertyType;
valueProperty.defaultValue = std::move(defaultValue);
}
inline std::size_t MaterialSettings::FindTextureProperty(std::string_view propertyName) const
{
for (std::size_t i = 0; i < m_textureProperties.size(); ++i)
{
if (m_textureProperties[i].name == propertyName)
return i; return i;
} }
return InvalidIndex; return InvalidPropertyIndex;
} }
inline std::size_t MaterialSettings::GetPredefinedBinding(PredefinedShaderBinding shaderBinding) const inline std::size_t MaterialSettings::FindValueProperty(std::string_view propertyName) const
{ {
return m_data.predefinedBindings[UnderlyingCast(shaderBinding)]; for (std::size_t i = 0; i < m_valueProperties.size(); ++i)
}
inline const std::shared_ptr<RenderPipelineLayout>& MaterialSettings::GetRenderPipelineLayout() const
{
return m_pipelineLayout;
}
inline const std::shared_ptr<UberShader>& MaterialSettings::GetShader(nzsl::ShaderStageType stage) const
{
return m_data.shaders[UnderlyingCast(stage)];
}
inline const std::vector<std::shared_ptr<UberShader>>& MaterialSettings::GetShaders() const
{
return m_data.shaders;
}
inline auto MaterialSettings::GetSharedUniformBlocks() const -> const std::vector<SharedUniformBlock>&
{
return m_data.sharedUniformBlocks;
}
inline std::size_t MaterialSettings::GetSharedUniformBlockIndex(const std::string_view& name) const
{
for (std::size_t i = 0; i < m_data.sharedUniformBlocks.size(); ++i)
{ {
if (m_data.sharedUniformBlocks[i].name == name) if (m_valueProperties[i].name == propertyName)
return i; return i;
} }
return InvalidIndex; return InvalidPropertyIndex;
} }
inline std::size_t MaterialSettings::GetSharedUniformBlockVariableOffset(std::size_t uniformBlockIndex, const std::string_view& name) const inline const MaterialPass* MaterialSettings::GetPass(std::size_t passIndex) const
{ {
assert(uniformBlockIndex < m_data.sharedUniformBlocks.size()); if (passIndex > m_materialPasses.size() || !m_materialPasses[passIndex].has_value())
return nullptr;
const std::vector<UniformVariable>& variables = m_data.sharedUniformBlocks[uniformBlockIndex].uniforms; return &m_materialPasses[passIndex].value();
for (std::size_t i = 0; i < variables.size(); ++i)
{
if (variables[i].name == name)
return i;
}
return InvalidIndex;
} }
inline auto MaterialSettings::GetTextures() const -> const std::vector<Texture>& inline const std::vector<std::optional<MaterialPass>>& MaterialSettings::GetPasses() const
{ {
return m_data.textures; return m_materialPasses;
} }
inline std::size_t MaterialSettings::GetTextureIndex(const std::string_view& name) const inline const std::vector<std::unique_ptr<PropertyHandler>>& MaterialSettings::GetPropertyHandlers() const
{ {
for (std::size_t i = 0; i < m_data.textures.size(); ++i) return m_propertyHandlers;
{
if (m_data.textures[i].name == name)
return i;
}
return InvalidIndex;
} }
inline auto MaterialSettings::GetUniformBlocks() const -> const std::vector<UniformBlock>& inline auto MaterialSettings::GetTextureProperty(std::size_t texturePropertyIndex) const -> const TextureProperty&
{ {
return m_data.uniformBlocks; assert(texturePropertyIndex < m_textureProperties.size());
return m_textureProperties[texturePropertyIndex];
} }
inline std::size_t MaterialSettings::GetUniformBlockIndex(const std::string_view& name) const inline std::size_t MaterialSettings::GetTexturePropertyCount() const
{ {
for (std::size_t i = 0; i < m_data.uniformBlocks.size(); ++i) return m_textureProperties.size();
{
if (m_data.uniformBlocks[i].name == name)
return i;
}
return InvalidIndex;
} }
inline std::size_t MaterialSettings::GetUniformBlockVariableOffset(std::size_t uniformBlockIndex, const std::string_view& name) const inline auto MaterialSettings::GetValueProperty(std::size_t valuePropertyIndex) const -> const ValueProperty&
{ {
assert(uniformBlockIndex < m_data.uniformBlocks.size()); assert(valuePropertyIndex < m_valueProperties.size());
return m_valueProperties[valuePropertyIndex];
const std::vector<UniformVariable>& variables = m_data.uniformBlocks[uniformBlockIndex].uniforms;
for (std::size_t i = 0; i < variables.size(); ++i)
{
if (variables[i].name == name)
return i;
}
return InvalidIndex;
} }
inline void MaterialSettings::BuildOption(std::vector<Option>& options, std::string optionName, const std::string& shaderOptionName) inline std::size_t MaterialSettings::GetValuePropertyCount() const
{ {
UInt32 optionHash = CRC32(shaderOptionName); return m_valueProperties.size();
options.push_back({
std::move(optionName),
optionHash
});
} }
inline MaterialSettings::Builder::Builder() template<typename T>
void MaterialSettings::AddValueProperty(std::string propertyName)
{ {
predefinedBindings.fill(InvalidIndex); return AddValueProperty(std::move(propertyName), TypeToMaterialPropertyType_v<T>);
}
template<typename T, typename U>
void MaterialSettings::AddValueProperty(std::string propertyName, U&& defaultValue)
{
constexpr std::size_t TypeIndex = TypeListFind<MaterialPropertyTypeList, T>;
auto& valueProperty = m_valueProperties.emplace_back();
valueProperty.name = std::move(propertyName);
valueProperty.type = TypeToMaterialPropertyType_v<T>;
valueProperty.defaultValue.emplace<TypeIndex>(std::forward<U>(defaultValue));
} }
} }

View File

@ -32,13 +32,13 @@ namespace Nz
const std::shared_ptr<RenderBuffer>& GetIndexBuffer(std::size_t subMeshIndex) const; const std::shared_ptr<RenderBuffer>& GetIndexBuffer(std::size_t subMeshIndex) const;
std::size_t GetIndexCount(std::size_t subMeshIndex) const; std::size_t GetIndexCount(std::size_t subMeshIndex) const;
const std::shared_ptr<Material>& GetMaterial(std::size_t subMeshIndex) const override; const std::shared_ptr<MaterialInstance>& GetMaterial(std::size_t subMeshIndex) const override;
std::size_t GetMaterialCount() const override; std::size_t GetMaterialCount() const override;
inline std::size_t GetSubMeshCount() const; inline std::size_t GetSubMeshCount() const;
const std::vector<RenderPipelineInfo::VertexBufferData>& GetVertexBufferData(std::size_t subMeshIndex) const; const std::vector<RenderPipelineInfo::VertexBufferData>& GetVertexBufferData(std::size_t subMeshIndex) const;
const std::shared_ptr<RenderBuffer>& GetVertexBuffer(std::size_t subMeshIndex) const; const std::shared_ptr<RenderBuffer>& GetVertexBuffer(std::size_t subMeshIndex) const;
inline void SetMaterial(std::size_t subMeshIndex, std::shared_ptr<Material> material); inline void SetMaterial(std::size_t subMeshIndex, std::shared_ptr<MaterialInstance> material);
Model& operator=(const Model&) = delete; Model& operator=(const Model&) = delete;
Model& operator=(Model&&) noexcept = default; Model& operator=(Model&&) noexcept = default;
@ -46,7 +46,7 @@ namespace Nz
private: private:
struct SubMeshData struct SubMeshData
{ {
std::shared_ptr<Material> material; std::shared_ptr<MaterialInstance> material;
std::vector<RenderPipelineInfo::VertexBufferData> vertexBufferData; std::vector<RenderPipelineInfo::VertexBufferData> vertexBufferData;
}; };

View File

@ -13,14 +13,14 @@ namespace Nz
return m_submeshes.size(); return m_submeshes.size();
} }
inline void Model::SetMaterial(std::size_t subMeshIndex, std::shared_ptr<Material> material) inline void Model::SetMaterial(std::size_t subMeshIndex, std::shared_ptr<MaterialInstance> material)
{ {
assert(subMeshIndex < m_submeshes.size()); assert(subMeshIndex < m_submeshes.size());
assert(material); assert(material);
if (m_submeshes[subMeshIndex].material != material) if (m_submeshes[subMeshIndex].material != material)
{ {
OnMaterialInvalidated(this, 0, material); OnMaterialInvalidated(this, subMeshIndex, material);
m_submeshes[subMeshIndex].material = std::move(material); m_submeshes[subMeshIndex].material = std::move(material);
OnElementInvalidated(this); OnElementInvalidated(this);

View File

@ -1,111 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PHONGLIGHTINGMATERIAL_HPP
#define NAZARA_GRAPHICS_PHONGLIGHTINGMATERIAL_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/BasicMaterial.hpp>
#include <Nazara/Graphics/MaterialPass.hpp>
namespace Nz
{
class NAZARA_GRAPHICS_API PhongLightingMaterial : public BasicMaterial
{
friend class MaterialPipeline;
public:
PhongLightingMaterial(MaterialPass& material);
Color GetAmbientColor() const;
inline const std::shared_ptr<Texture>& GetEmissiveMap() const;
inline const TextureSamplerInfo& GetEmissiveSampler() const;
inline const std::shared_ptr<Texture>& GetHeightMap() const;
inline const TextureSamplerInfo& GetHeightSampler() const;
inline const std::shared_ptr<Texture>& GetNormalMap() const;
inline const TextureSamplerInfo& GetNormalSampler() const;
float GetShininess() const;
Color GetSpecularColor() const;
inline const std::shared_ptr<Texture>& GetSpecularMap() const;
inline const TextureSamplerInfo& GetSpecularSampler() const;
inline bool HasAmbientColor() const;
inline bool HasEmissiveMap() const;
inline bool HasHeightMap() const;
inline bool HasNormalMap() const;
inline bool HasShininess() const;
inline bool HasSpecularColor() const;
inline bool HasSpecularMap() const;
void SetAmbientColor(const Color& ambient);
inline void SetEmissiveMap(std::shared_ptr<Texture> emissiveMap);
inline void SetEmissiveSampler(TextureSamplerInfo emissiveSampler);
inline void SetHeightMap(std::shared_ptr<Texture> heightMap);
inline void SetHeightSampler(TextureSamplerInfo heightSampler);
inline void SetNormalMap(std::shared_ptr<Texture> normalMap);
inline void SetNormalSampler(TextureSamplerInfo normalSampler);
void SetShininess(float shininess);
void SetSpecularColor(const Color& specular);
inline void SetSpecularMap(std::shared_ptr<Texture> specularMap);
inline void SetSpecularSampler(TextureSamplerInfo specularSampler);
static const std::shared_ptr<MaterialSettings>& GetSettings();
protected:
struct PhongOptionIndexes
{
std::size_t hasEmissiveMap;
std::size_t hasHeightMap;
std::size_t hasNormalMap;
std::size_t hasSpecularMap;
};
struct PhongUniformOffsets
{
std::size_t ambientColor;
std::size_t shininess;
std::size_t totalSize;
std::size_t specularColor;
};
struct PhongTextureIndexes
{
std::size_t emissive;
std::size_t height;
std::size_t normal;
std::size_t specular;
};
struct PhongBuildOptions : BasicBuildOptions
{
PhongUniformOffsets phongOffsets;
PhongOptionIndexes* phongOptionIndexes = nullptr;
PhongTextureIndexes* phongTextureIndexes = nullptr;
};
PhongOptionIndexes m_phongOptionIndexes;
PhongTextureIndexes m_phongTextureIndexes;
PhongUniformOffsets m_phongUniformOffsets;
static MaterialSettings::Builder Build(PhongBuildOptions& options);
static std::vector<std::shared_ptr<UberShader>> BuildShaders();
static std::pair<PhongUniformOffsets, nzsl::FieldOffsets> BuildUniformOffsets();
private:
static bool Initialize();
static void Uninitialize();
static std::shared_ptr<MaterialSettings> s_phongMaterialSettings;
static std::size_t s_phongUniformBlockIndex;
static PhongOptionIndexes s_phongOptionIndexes;
static PhongTextureIndexes s_phongTextureIndexes;
static PhongUniformOffsets s_phongUniformOffsets;
};
}
#include <Nazara/Graphics/PhongLightingMaterial.inl>
#endif // NAZARA_GRAPHICS_PHONGLIGHTINGMATERIAL_HPP

View File

@ -1,160 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/PhongLightingMaterial.hpp>
#include <Nazara/Core/ErrorFlags.hpp>
#include <memory>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline const std::shared_ptr<Texture>& PhongLightingMaterial::GetEmissiveMap() const
{
NazaraAssert(HasEmissiveMap(), "Material has no emissive map slot");
return GetMaterial().GetTexture(m_phongTextureIndexes.emissive);
}
inline const TextureSamplerInfo& PhongLightingMaterial::GetEmissiveSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no emissive map slot");
return GetMaterial().GetTextureSampler(m_phongTextureIndexes.emissive);
}
inline const std::shared_ptr<Texture>& PhongLightingMaterial::GetHeightMap() const
{
NazaraAssert(HasHeightMap(), "Material has no height map slot");
return GetMaterial().GetTexture(m_phongTextureIndexes.height);
}
inline const TextureSamplerInfo& PhongLightingMaterial::GetHeightSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no height map slot");
return GetMaterial().GetTextureSampler(m_phongTextureIndexes.height);
}
inline const std::shared_ptr<Texture>& PhongLightingMaterial::GetNormalMap() const
{
NazaraAssert(HasNormalMap(), "Material has no normal map slot");
return GetMaterial().GetTexture(m_phongTextureIndexes.normal);
}
inline const TextureSamplerInfo& PhongLightingMaterial::GetNormalSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no normal map slot");
return GetMaterial().GetTextureSampler(m_phongTextureIndexes.normal);
}
inline const std::shared_ptr<Texture>& PhongLightingMaterial::GetSpecularMap() const
{
NazaraAssert(HasSpecularMap(), "Material has no specular map slot");
return GetMaterial().GetTexture(m_phongTextureIndexes.specular);
}
inline const TextureSamplerInfo& PhongLightingMaterial::GetSpecularSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no specular map slot");
return GetMaterial().GetTextureSampler(m_phongTextureIndexes.specular);
}
inline bool PhongLightingMaterial::HasAmbientColor() const
{
return m_phongUniformOffsets.ambientColor != MaterialSettings::InvalidIndex;
}
inline bool PhongLightingMaterial::HasEmissiveMap() const
{
return m_phongTextureIndexes.emissive != MaterialSettings::InvalidIndex;
}
inline bool PhongLightingMaterial::HasHeightMap() const
{
return m_phongTextureIndexes.height != MaterialSettings::InvalidIndex;
}
inline bool PhongLightingMaterial::HasNormalMap() const
{
return m_phongTextureIndexes.normal != MaterialSettings::InvalidIndex;
}
inline bool PhongLightingMaterial::HasShininess() const
{
return m_phongUniformOffsets.shininess != MaterialSettings::InvalidIndex;
}
inline bool PhongLightingMaterial::HasSpecularColor() const
{
return m_phongUniformOffsets.specularColor != MaterialSettings::InvalidIndex;
}
inline bool PhongLightingMaterial::HasSpecularMap() const
{
return m_phongTextureIndexes.specular != MaterialSettings::InvalidIndex;
}
inline void PhongLightingMaterial::SetEmissiveMap(std::shared_ptr<Texture> emissiveMap)
{
NazaraAssert(HasEmissiveMap(), "Material has no emissive map slot");
bool hasEmissiveMap = (emissiveMap != nullptr);
GetMaterial().SetTexture(m_phongTextureIndexes.emissive, std::move(emissiveMap));
if (m_phongOptionIndexes.hasEmissiveMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_phongOptionIndexes.hasEmissiveMap, hasEmissiveMap);
}
inline void PhongLightingMaterial::SetEmissiveSampler(TextureSamplerInfo emissiveSampler)
{
NazaraAssert(HasEmissiveMap(), "Material has no emissive map slot");
GetMaterial().SetTextureSampler(m_phongTextureIndexes.emissive, std::move(emissiveSampler));
}
inline void PhongLightingMaterial::SetHeightMap(std::shared_ptr<Texture> heightMap)
{
NazaraAssert(HasHeightMap(), "Material has no specular map slot");
bool hasHeightMap = (heightMap != nullptr);
GetMaterial().SetTexture(m_phongTextureIndexes.height, std::move(heightMap));
if (m_phongOptionIndexes.hasHeightMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_phongOptionIndexes.hasHeightMap, hasHeightMap);
}
inline void PhongLightingMaterial::SetHeightSampler(TextureSamplerInfo heightSampler)
{
NazaraAssert(HasHeightMap(), "Material has no height map slot");
GetMaterial().SetTextureSampler(m_phongTextureIndexes.height, std::move(heightSampler));
}
inline void PhongLightingMaterial::SetNormalMap(std::shared_ptr<Texture> normalMap)
{
NazaraAssert(HasNormalMap(), "Material has no normal map slot");
bool hasNormalMap = (normalMap != nullptr);
GetMaterial().SetTexture(m_phongTextureIndexes.normal, std::move(normalMap));
if (m_phongOptionIndexes.hasNormalMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_phongOptionIndexes.hasNormalMap, hasNormalMap);
}
inline void PhongLightingMaterial::SetNormalSampler(TextureSamplerInfo normalSampler)
{
NazaraAssert(HasNormalMap(), "Material has no normal map slot");
GetMaterial().SetTextureSampler(m_phongTextureIndexes.normal, std::move(normalSampler));
}
inline void PhongLightingMaterial::SetSpecularMap(std::shared_ptr<Texture> specularMap)
{
NazaraAssert(HasNormalMap(), "Material has no specular map slot");
bool hasSpecularMap = (specularMap != nullptr);
GetMaterial().SetTexture(m_phongTextureIndexes.specular, std::move(specularMap));
if (m_phongOptionIndexes.hasSpecularMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_phongOptionIndexes.hasSpecularMap, hasSpecularMap);
}
inline void PhongLightingMaterial::SetSpecularSampler(TextureSamplerInfo specularSampler)
{
NazaraAssert(HasSpecularMap(), "Material has no specular map slot");
GetMaterial().SetTextureSampler(m_phongTextureIndexes.specular, std::move(specularSampler));
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -1,125 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PHYSICALLYBASEDMATERIAL_HPP
#define NAZARA_GRAPHICS_PHYSICALLYBASEDMATERIAL_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/BasicMaterial.hpp>
#include <Nazara/Graphics/MaterialPass.hpp>
namespace Nz
{
class NAZARA_GRAPHICS_API PhysicallyBasedMaterial : public BasicMaterial
{
friend class MaterialPipeline;
public:
PhysicallyBasedMaterial(MaterialPass& material);
Color GetAmbientColor() const;
inline const std::shared_ptr<Texture>& GetEmissiveMap() const;
inline const TextureSamplerInfo& GetEmissiveSampler() const;
inline const std::shared_ptr<Texture>& GetHeightMap() const;
inline const TextureSamplerInfo& GetHeightSampler() const;
inline const std::shared_ptr<Texture>& GetMetallicMap() const;
inline const TextureSamplerInfo& GetMetallicSampler() const;
inline const std::shared_ptr<Texture>& GetNormalMap() const;
inline const TextureSamplerInfo& GetNormalSampler() const;
inline const std::shared_ptr<Texture>& GetRoughnessMap() const;
inline const TextureSamplerInfo& GetRoughnessSampler() const;
float GetShininess() const;
Color GetSpecularColor() const;
inline const std::shared_ptr<Texture>& GetSpecularMap() const;
inline const TextureSamplerInfo& GetSpecularSampler() const;
inline bool HasAmbientColor() const;
inline bool HasEmissiveMap() const;
inline bool HasHeightMap() const;
inline bool HasMetallicMap() const;
inline bool HasNormalMap() const;
inline bool HasRoughnessMap() const;
inline bool HasShininess() const;
inline bool HasSpecularColor() const;
inline bool HasSpecularMap() const;
void SetAmbientColor(const Color& ambient);
inline void SetEmissiveMap(std::shared_ptr<Texture> emissiveMap);
inline void SetEmissiveSampler(TextureSamplerInfo emissiveSampler);
inline void SetHeightMap(std::shared_ptr<Texture> heightMap);
inline void SetHeightSampler(TextureSamplerInfo heightSampler);
inline void SetMetallicMap(std::shared_ptr<Texture> metallicMap);
inline void SetMetallicSampler(TextureSamplerInfo metallicSampler);
inline void SetNormalMap(std::shared_ptr<Texture> normalMap);
inline void SetNormalSampler(TextureSamplerInfo normalSampler);
inline void SetRoughnessMap(std::shared_ptr<Texture> roughnessMap);
inline void SetRoughnessSampler(TextureSamplerInfo roughnessSampler);
void SetShininess(float shininess);
void SetSpecularColor(const Color& specular);
inline void SetSpecularMap(std::shared_ptr<Texture> specularMap);
inline void SetSpecularSampler(TextureSamplerInfo specularSampler);
static const std::shared_ptr<MaterialSettings>& GetSettings();
protected:
struct PbrOptionIndexes
{
std::size_t hasEmissiveMap;
std::size_t hasHeightMap;
std::size_t hasMetallicMap;
std::size_t hasNormalMap;
std::size_t hasRoughnessMap;
std::size_t hasSpecularMap;
};
struct PbrUniformOffsets
{
std::size_t ambientColor;
std::size_t shininess;
std::size_t totalSize;
std::size_t specularColor;
};
struct PbrTextureIndexes
{
std::size_t emissive;
std::size_t height;
std::size_t metallic;
std::size_t roughness;
std::size_t normal;
std::size_t specular;
};
struct PbrBuildOptions : BasicBuildOptions
{
PbrUniformOffsets pbrOffsets;
PbrOptionIndexes* pbrOptionIndexes = nullptr;
PbrTextureIndexes* pbrTextureIndexes = nullptr;
};
PbrOptionIndexes m_pbrOptionIndexes;
PbrTextureIndexes m_pbrTextureIndexes;
PbrUniformOffsets m_pbrUniformOffsets;
static MaterialSettings::Builder Build(PbrBuildOptions& options);
static std::vector<std::shared_ptr<UberShader>> BuildShaders();
static std::pair<PbrUniformOffsets, nzsl::FieldOffsets> BuildUniformOffsets();
private:
static bool Initialize();
static void Uninitialize();
static std::shared_ptr<MaterialSettings> s_pbrMaterialSettings;
static std::size_t s_pbrUniformBlockIndex;
static PbrOptionIndexes s_pbrOptionIndexes;
static PbrTextureIndexes s_pbrTextureIndexes;
static PbrUniformOffsets s_pbrUniformOffsets;
};
}
#include <Nazara/Graphics/PhysicallyBasedMaterial.inl>
#endif // NAZARA_GRAPHICS_PHYSICALLYBASEDMATERIAL_HPP

View File

@ -1,226 +0,0 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/PhysicallyBasedMaterial.hpp>
#include <Nazara/Core/ErrorFlags.hpp>
#include <memory>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline const std::shared_ptr<Texture>& PhysicallyBasedMaterial::GetEmissiveMap() const
{
NazaraAssert(HasEmissiveMap(), "Material has no emissive map slot");
return GetMaterial().GetTexture(m_pbrTextureIndexes.emissive);
}
inline const TextureSamplerInfo& PhysicallyBasedMaterial::GetEmissiveSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no emissive map slot");
return GetMaterial().GetTextureSampler(m_pbrTextureIndexes.emissive);
}
inline const std::shared_ptr<Texture>& PhysicallyBasedMaterial::GetHeightMap() const
{
NazaraAssert(HasHeightMap(), "Material has no height map slot");
return GetMaterial().GetTexture(m_pbrTextureIndexes.height);
}
inline const TextureSamplerInfo& PhysicallyBasedMaterial::GetHeightSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no height map slot");
return GetMaterial().GetTextureSampler(m_pbrTextureIndexes.height);
}
inline const std::shared_ptr<Texture>& PhysicallyBasedMaterial::GetMetallicMap() const
{
NazaraAssert(HasMetallicMap(), "Material has no metallic map slot");
return GetMaterial().GetTexture(m_pbrTextureIndexes.metallic);
}
inline const TextureSamplerInfo& PhysicallyBasedMaterial::GetMetallicSampler() const
{
NazaraAssert(HasMetallicMap(), "Material has no metallic map slot");
return GetMaterial().GetTextureSampler(m_pbrTextureIndexes.metallic);
}
inline const std::shared_ptr<Texture>& PhysicallyBasedMaterial::GetNormalMap() const
{
NazaraAssert(HasNormalMap(), "Material has no normal map slot");
return GetMaterial().GetTexture(m_pbrTextureIndexes.normal);
}
inline const TextureSamplerInfo& PhysicallyBasedMaterial::GetNormalSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no normal map slot");
return GetMaterial().GetTextureSampler(m_pbrTextureIndexes.normal);
}
inline const std::shared_ptr<Texture>& PhysicallyBasedMaterial::GetRoughnessMap() const
{
NazaraAssert(HasRoughnessMap(), "Material has no roughness map slot");
return GetMaterial().GetTexture(m_pbrTextureIndexes.roughness);
}
inline const TextureSamplerInfo& PhysicallyBasedMaterial::GetRoughnessSampler() const
{
NazaraAssert(HasRoughnessMap(), "Material has no roughness map slot");
return GetMaterial().GetTextureSampler(m_pbrTextureIndexes.roughness);
}
inline const std::shared_ptr<Texture>& PhysicallyBasedMaterial::GetSpecularMap() const
{
NazaraAssert(HasSpecularMap(), "Material has no specular map slot");
return GetMaterial().GetTexture(m_pbrTextureIndexes.specular);
}
inline const TextureSamplerInfo& PhysicallyBasedMaterial::GetSpecularSampler() const
{
NazaraAssert(HasSpecularMap(), "Material has no specular map slot");
return GetMaterial().GetTextureSampler(m_pbrTextureIndexes.specular);
}
inline bool PhysicallyBasedMaterial::HasAmbientColor() const
{
return m_pbrUniformOffsets.ambientColor != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasEmissiveMap() const
{
return m_pbrTextureIndexes.emissive != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasHeightMap() const
{
return m_pbrTextureIndexes.height != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasMetallicMap() const
{
return m_pbrTextureIndexes.metallic != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasNormalMap() const
{
return m_pbrTextureIndexes.normal != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasRoughnessMap() const
{
return m_pbrTextureIndexes.roughness != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasShininess() const
{
return m_pbrUniformOffsets.shininess != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasSpecularColor() const
{
return m_pbrUniformOffsets.specularColor != MaterialSettings::InvalidIndex;
}
inline bool PhysicallyBasedMaterial::HasSpecularMap() const
{
return m_pbrTextureIndexes.specular != MaterialSettings::InvalidIndex;
}
inline void PhysicallyBasedMaterial::SetEmissiveMap(std::shared_ptr<Texture> emissiveMap)
{
NazaraAssert(HasEmissiveMap(), "Material has no emissive map slot");
bool hasEmissiveMap = (emissiveMap != nullptr);
GetMaterial().SetTexture(m_pbrTextureIndexes.emissive, std::move(emissiveMap));
if (m_pbrOptionIndexes.hasEmissiveMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_pbrOptionIndexes.hasEmissiveMap, hasEmissiveMap);
}
inline void PhysicallyBasedMaterial::SetEmissiveSampler(TextureSamplerInfo emissiveSampler)
{
NazaraAssert(HasEmissiveMap(), "Material has no emissive map slot");
GetMaterial().SetTextureSampler(m_pbrTextureIndexes.emissive, std::move(emissiveSampler));
}
inline void PhysicallyBasedMaterial::SetHeightMap(std::shared_ptr<Texture> heightMap)
{
NazaraAssert(HasHeightMap(), "Material has no specular map slot");
bool hasHeightMap = (heightMap != nullptr);
GetMaterial().SetTexture(m_pbrTextureIndexes.height, std::move(heightMap));
if (m_pbrOptionIndexes.hasHeightMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_pbrOptionIndexes.hasHeightMap, hasHeightMap);
}
inline void PhysicallyBasedMaterial::SetHeightSampler(TextureSamplerInfo heightSampler)
{
NazaraAssert(HasHeightMap(), "Material has no height map slot");
GetMaterial().SetTextureSampler(m_pbrTextureIndexes.height, std::move(heightSampler));
}
inline void PhysicallyBasedMaterial::SetMetallicMap(std::shared_ptr<Texture> metallicMap)
{
NazaraAssert(HasMetallicMap(), "Material has no metallic map slot");
bool hasMetallicMap = (metallicMap != nullptr);
GetMaterial().SetTexture(m_pbrTextureIndexes.metallic, std::move(metallicMap));
if (m_pbrOptionIndexes.hasMetallicMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_pbrOptionIndexes.hasMetallicMap, hasMetallicMap);
}
inline void PhysicallyBasedMaterial::SetMetallicSampler(TextureSamplerInfo metallicSampler)
{
NazaraAssert(HasMetallicMap(), "Material has no metallic map slot");
GetMaterial().SetTextureSampler(m_pbrTextureIndexes.metallic, std::move(metallicSampler));
}
inline void PhysicallyBasedMaterial::SetNormalMap(std::shared_ptr<Texture> normalMap)
{
NazaraAssert(HasNormalMap(), "Material has no normal map slot");
bool hasNormalMap = (normalMap != nullptr);
GetMaterial().SetTexture(m_pbrTextureIndexes.normal, std::move(normalMap));
if (m_pbrOptionIndexes.hasNormalMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_pbrOptionIndexes.hasNormalMap, hasNormalMap);
}
inline void PhysicallyBasedMaterial::SetNormalSampler(TextureSamplerInfo normalSampler)
{
NazaraAssert(HasNormalMap(), "Material has no normal map slot");
GetMaterial().SetTextureSampler(m_pbrTextureIndexes.normal, std::move(normalSampler));
}
inline void PhysicallyBasedMaterial::SetRoughnessMap(std::shared_ptr<Texture> roughnessMap)
{
NazaraAssert(HasRoughnessMap(), "Material has no roughness map slot");
bool hasRoughnessMap = (roughnessMap != nullptr);
GetMaterial().SetTexture(m_pbrTextureIndexes.roughness, std::move(roughnessMap));
if (m_pbrOptionIndexes.hasRoughnessMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_pbrOptionIndexes.hasRoughnessMap, hasRoughnessMap);
}
inline void PhysicallyBasedMaterial::SetRoughnessSampler(TextureSamplerInfo metallicSampler)
{
NazaraAssert(HasRoughnessMap(), "Material has no roughness map slot");
GetMaterial().SetTextureSampler(m_pbrTextureIndexes.roughness, std::move(metallicSampler));
}
inline void PhysicallyBasedMaterial::SetSpecularMap(std::shared_ptr<Texture> specularMap)
{
NazaraAssert(HasNormalMap(), "Material has no specular map slot");
bool hasSpecularMap = (specularMap != nullptr);
GetMaterial().SetTexture(m_pbrTextureIndexes.specular, std::move(specularMap));
if (m_pbrOptionIndexes.hasSpecularMap != MaterialSettings::InvalidIndex)
GetMaterial().SetOptionValue(m_pbrOptionIndexes.hasSpecularMap, hasSpecularMap);
}
inline void PhysicallyBasedMaterial::SetSpecularSampler(TextureSamplerInfo specularSampler)
{
NazaraAssert(HasSpecularMap(), "Material has no specular map slot");
GetMaterial().SetTextureSampler(m_pbrTextureIndexes.specular, std::move(specularSampler));
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -0,0 +1,31 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PREDEFINEDMATERIALS_HPP
#define NAZARA_GRAPHICS_PREDEFINEDMATERIALS_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
namespace Nz
{
class MaterialSettings;
class NAZARA_GRAPHICS_API PredefinedMaterials
{
public:
PredefinedMaterials() = delete;
~PredefinedMaterials() = delete;
static void AddBasicSettings(MaterialSettings& settings);
static void AddPbrSettings(MaterialSettings& settings);
static void AddPhongSettings(MaterialSettings& settings);
};
}
#include <Nazara/Graphics/PredefinedMaterials.inl>
#endif // NAZARA_GRAPHICS_PREDEFINEDMATERIALS_HPP

View File

@ -2,15 +2,11 @@
// This file is part of the "Nazara Engine - Graphics module" // This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp // For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/DepthMaterial.hpp> #include <Nazara/Graphics/PredefinedMaterials.hpp>
#include <Nazara/Graphics/Debug.hpp> #include <Nazara/Graphics/Debug.hpp>
namespace Nz namespace Nz
{ {
inline const std::shared_ptr<MaterialSettings>& DepthMaterial::GetSettings()
{
return s_depthMaterialSettings;
}
} }
#include <Nazara/Graphics/DebugOff.hpp> #include <Nazara/Graphics/DebugOff.hpp>

View File

@ -35,7 +35,6 @@ namespace Nz
static constexpr std::size_t MaxLightCount = 3; static constexpr std::size_t MaxLightCount = 3;
static PredefinedLightData GetOffsets(); static PredefinedLightData GetOffsets();
static MaterialSettings::SharedUniformBlock GetUniformBlock(UInt32 bindingIndex, nzsl::ShaderStageTypeFlags shaderStages);
}; };
struct NAZARA_GRAPHICS_API PredefinedInstanceData struct NAZARA_GRAPHICS_API PredefinedInstanceData
@ -45,7 +44,6 @@ namespace Nz
std::size_t worldMatrixOffset; std::size_t worldMatrixOffset;
static PredefinedInstanceData GetOffsets(); static PredefinedInstanceData GetOffsets();
static MaterialSettings::SharedUniformBlock GetUniformBlock(UInt32 bindingIndex, nzsl::ShaderStageTypeFlags shaderStages);
}; };
struct NAZARA_GRAPHICS_API PredefinedSkeletalData struct NAZARA_GRAPHICS_API PredefinedSkeletalData
@ -56,7 +54,6 @@ namespace Nz
static constexpr std::size_t MaxMatricesCount = 256; static constexpr std::size_t MaxMatricesCount = 256;
static PredefinedSkeletalData GetOffsets(); static PredefinedSkeletalData GetOffsets();
static MaterialSettings::SharedUniformBlock GetUniformBlock(UInt32 bindingIndex, nzsl::ShaderStageTypeFlags shaderStages);
}; };
struct NAZARA_GRAPHICS_API PredefinedViewerData struct NAZARA_GRAPHICS_API PredefinedViewerData
@ -73,7 +70,6 @@ namespace Nz
std::size_t viewProjMatrixOffset; std::size_t viewProjMatrixOffset;
static PredefinedViewerData GetOffsets(); static PredefinedViewerData GetOffsets();
static MaterialSettings::SharedUniformBlock GetUniformBlock(UInt32 bindingIndex, nzsl::ShaderStageTypeFlags shaderStages);
}; };
} }

View File

@ -0,0 +1,43 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PROPERTYHANDLER_OPTIONVALUEPROPERTYHANDLER_HPP
#define NAZARA_GRAPHICS_PROPERTYHANDLER_OPTIONVALUEPROPERTYHANDLER_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/PropertyHandler/PropertyHandler.hpp>
namespace Nz
{
class NAZARA_GRAPHICS_API OptionValuePropertyHandler : public PropertyHandler
{
public:
inline OptionValuePropertyHandler(std::string propertyName, std::string optionName);
OptionValuePropertyHandler(const OptionValuePropertyHandler&) = default;
OptionValuePropertyHandler(OptionValuePropertyHandler&&) = delete;
~OptionValuePropertyHandler() = default;
bool NeedsUpdateOnValueUpdate(std::size_t updatedPropertyIndex) const override;
void Setup(const Material& material, const ShaderReflection& reflection) override;
void Update(MaterialInstance& materialInstance) const override;
OptionValuePropertyHandler& operator=(const OptionValuePropertyHandler&) = delete;
OptionValuePropertyHandler& operator=(OptionValuePropertyHandler&&) = delete;
private:
std::size_t m_propertyIndex;
std::string m_propertyName;
std::string m_optionName;
UInt32 m_optionHash;
};
}
#include <Nazara/Graphics/PropertyHandler/OptionValuePropertyHandler.inl>
#endif // NAZARA_GRAPHICS_PROPERTYHANDLER_OPTIONVALUEPROPERTYHANDLER_HPP

View File

@ -0,0 +1,17 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/PropertyHandler/OptionValuePropertyHandler.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline OptionValuePropertyHandler::OptionValuePropertyHandler(std::string propertyName, std::string optionName) :
m_propertyName(std::move(propertyName)),
m_optionName(std::move(optionName))
{
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -0,0 +1,54 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PROPERTYHANDLER_PROPERTYHANDLER_HPP
#define NAZARA_GRAPHICS_PROPERTYHANDLER_PROPERTYHANDLER_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Core/Enums.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <NZSL/Enums.hpp>
namespace Nz
{
class Material;
class MaterialInstance;
class ShaderReflection;
class NAZARA_GRAPHICS_API PropertyHandler
{
public:
PropertyHandler() = default;
PropertyHandler(const PropertyHandler&) = delete;
PropertyHandler(PropertyHandler&&) = delete;
virtual ~PropertyHandler();
virtual bool NeedsUpdateOnTextureUpdate(std::size_t updatedTexturePropertyIndex) const;
virtual bool NeedsUpdateOnValueUpdate(std::size_t updatedValuePropertyIndex) const;
virtual void Setup(const Material& material, const ShaderReflection& reflection) = 0;
virtual void Update(MaterialInstance& materialInstance) const = 0;
PropertyHandler& operator=(const PropertyHandler&) = delete;
PropertyHandler& operator=(PropertyHandler&&) = delete;
struct SamplerData
{
std::size_t textureIndex;
};
struct UniformValue
{
std::size_t uniformBufferIndex;
std::size_t offset;
};
};
}
#include <Nazara/Graphics/PropertyHandler/PropertyHandler.inl>
#endif // NAZARA_GRAPHICS_PROPERTYHANDLER_PROPERTYHANDLER_HPP

View File

@ -0,0 +1,13 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/PropertyHandler/PropertyHandler.hpp>
#include <Nazara/Core/Error.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -0,0 +1,48 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PROPERTYHANDLER_TEXTUREPROPERTYHANDLER_HPP
#define NAZARA_GRAPHICS_PROPERTYHANDLER_TEXTUREPROPERTYHANDLER_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/PropertyHandler/PropertyHandler.hpp>
#include <string>
namespace Nz
{
class NAZARA_GRAPHICS_API TexturePropertyHandler : public PropertyHandler
{
public:
inline TexturePropertyHandler(std::string propertyName);
inline TexturePropertyHandler(std::string propertyName, std::string optionName);
inline TexturePropertyHandler(std::string propertyName, std::string samplerTag, std::string optionName);
TexturePropertyHandler(const TexturePropertyHandler&) = delete;
TexturePropertyHandler(TexturePropertyHandler&&) = delete;
~TexturePropertyHandler() = default;
bool NeedsUpdateOnTextureUpdate(std::size_t updatedPropertyIndex) const override;
void Setup(const Material& material, const ShaderReflection& reflection) override;
void Update(MaterialInstance& materialInstance) const override;
TexturePropertyHandler& operator=(const TexturePropertyHandler&) = delete;
TexturePropertyHandler& operator=(TexturePropertyHandler&&) = delete;
private:
std::size_t m_propertyIndex;
std::size_t m_textureIndex;
std::string m_optionName;
std::string m_propertyName;
std::string m_samplerTag;
UInt32 m_optionHash;
};
}
#include <Nazara/Graphics/PropertyHandler/TexturePropertyHandler.inl>
#endif // NAZARA_GRAPHICS_PROPERTYHANDLER_TEXTUREPROPERTYHANDLER_HPP

View File

@ -0,0 +1,31 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/PropertyHandler/TexturePropertyHandler.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline TexturePropertyHandler::TexturePropertyHandler(std::string propertyName) :
m_propertyName(std::move(propertyName)),
m_samplerTag(m_propertyName)
{
}
inline TexturePropertyHandler::TexturePropertyHandler(std::string propertyName, std::string optionName) :
m_optionName(std::move(optionName)),
m_propertyName(std::move(propertyName)),
m_samplerTag(m_propertyName)
{
}
inline TexturePropertyHandler::TexturePropertyHandler(std::string propertyName, std::string samplerTag, std::string optionName) :
m_optionName(std::move(optionName)),
m_propertyName(std::move(propertyName)),
m_samplerTag(std::move(samplerTag))
{
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -0,0 +1,47 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_PROPERTYHANDLER_UNIFORMVALUEPROPERTYHANDLER_HPP
#define NAZARA_GRAPHICS_PROPERTYHANDLER_UNIFORMVALUEPROPERTYHANDLER_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/PropertyHandler/PropertyHandler.hpp>
namespace Nz
{
class NAZARA_GRAPHICS_API UniformValuePropertyHandler : public PropertyHandler
{
public:
inline UniformValuePropertyHandler(std::string propertyName, std::string blockTag = "Settings");
inline UniformValuePropertyHandler(std::string propertyName, std::string memberTag, std::string blockTag = "Settings");
UniformValuePropertyHandler(const UniformValuePropertyHandler&) = delete;
UniformValuePropertyHandler(UniformValuePropertyHandler&&) = delete;
~UniformValuePropertyHandler() = default;
bool NeedsUpdateOnValueUpdate(std::size_t updatedPropertyIndex) const override;
void Setup(const Material& material, const ShaderReflection& reflection) override;
void Update(MaterialInstance& materialInstance) const override;
UniformValuePropertyHandler& operator=(const UniformValuePropertyHandler&) = delete;
UniformValuePropertyHandler& operator=(UniformValuePropertyHandler&&) = delete;
private:
std::size_t m_propertyIndex;
std::size_t m_offset;
std::size_t m_size;
std::size_t m_uniformBlockIndex;
std::string m_blockTag;
std::string m_propertyName;
std::string m_memberTag;
};
}
#include <Nazara/Graphics/PropertyHandler/UniformValuePropertyHandler.inl>
#endif // NAZARA_GRAPHICS_PROPERTYHANDLER_UNIFORMVALUEPROPERTYHANDLER_HPP

View File

@ -0,0 +1,25 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/PropertyHandler/UniformValuePropertyHandler.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline UniformValuePropertyHandler::UniformValuePropertyHandler(std::string propertyName, std::string blockTag) :
m_blockTag(std::move(blockTag)),
m_propertyName(std::move(propertyName)),
m_memberTag(m_propertyName)
{
}
inline UniformValuePropertyHandler::UniformValuePropertyHandler(std::string propertyName, std::string memberTag, std::string blockTag) :
m_blockTag(std::move(blockTag)),
m_propertyName(std::move(propertyName)),
m_memberTag(std::move(memberTag))
{
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -0,0 +1,54 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_RENDERBUFFERPOOL_HPP
#define NAZARA_GRAPHICS_RENDERBUFFERPOOL_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Renderer/RenderBufferView.hpp>
#include <Nazara/Utils/Bitset.hpp>
#include <vector>
namespace Nz
{
class RenderBuffer;
class RenderDevice;
class NAZARA_GRAPHICS_API RenderBufferPool
{
public:
RenderBufferPool(std::shared_ptr<RenderDevice> renderDevice, BufferType bufferType, std::size_t bufferSize, std::size_t bufferPerBlock = 2048);
RenderBufferPool(const RenderBufferPool&) = delete;
RenderBufferPool(RenderBufferPool&&) = delete;
~RenderBufferPool() = default;
RenderBufferView Allocate(std::size_t& index);
void Free(std::size_t index);
inline UInt64 GetBufferAlignedSize() const;
inline UInt64 GetBufferPerBlock() const;
inline UInt64 GetBufferSize() const;
inline BufferType GetBufferType() const;
RenderBufferPool& operator=(const RenderBufferPool&) = delete;
RenderBufferPool& operator=(RenderBufferPool&&) = delete;
private:
UInt64 m_bufferAlignedSize;
UInt64 m_bufferPerBlock;
UInt64 m_bufferSize;
std::shared_ptr<RenderDevice> m_renderDevice;
std::vector<std::shared_ptr<RenderBuffer>> m_bufferBlocks;
Bitset<UInt64> m_availableEntries;
BufferType m_bufferType;
};
}
#include <Nazara/Graphics/RenderBufferPool.inl>
#endif // NAZARA_GRAPHICS_RENDERBUFFERPOOL_HPP

View File

@ -0,0 +1,31 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/RenderBufferPool.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline UInt64 Nz::RenderBufferPool::GetBufferAlignedSize() const
{
return m_bufferAlignedSize;
}
inline UInt64 RenderBufferPool::GetBufferPerBlock() const
{
return m_bufferPerBlock;
}
inline UInt64 RenderBufferPool::GetBufferSize() const
{
return m_bufferSize;
}
inline BufferType RenderBufferPool::GetBufferType() const
{
return m_bufferType;
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -13,7 +13,7 @@
namespace Nz namespace Nz
{ {
class MaterialPass; class MaterialInstance;
class RenderPipeline; class RenderPipeline;
class Skeleton; class Skeleton;
class VertexDeclaration; class VertexDeclaration;
@ -27,7 +27,7 @@ namespace Nz
inline void Clear(); inline void Clear();
inline std::size_t FetchLayerIndex(int renderLayer) const; inline std::size_t FetchLayerIndex(int renderLayer) const;
inline std::size_t FetchMaterialPassIndex(const MaterialPass* materialPass) const; inline std::size_t FetchMaterialInstanceIndex(const MaterialInstance* materialInstance) const;
inline std::size_t FetchPipelineIndex(const RenderPipeline* pipeline) const; inline std::size_t FetchPipelineIndex(const RenderPipeline* pipeline) const;
inline std::size_t FetchSkeletonIndex(const Skeleton* skeleton) const; inline std::size_t FetchSkeletonIndex(const Skeleton* skeleton) const;
inline std::size_t FetchVertexBuffer(const RenderBuffer* vertexBuffer) const; inline std::size_t FetchVertexBuffer(const RenderBuffer* vertexBuffer) const;
@ -36,7 +36,7 @@ namespace Nz
inline void Finalize(); inline void Finalize();
inline void RegisterLayer(int renderLayer); inline void RegisterLayer(int renderLayer);
inline void RegisterMaterialPass(const MaterialPass* materialPass); inline void RegisterMaterialInstance(const MaterialInstance* materialInstance);
inline void RegisterPipeline(const RenderPipeline* pipeline); inline void RegisterPipeline(const RenderPipeline* pipeline);
inline void RegisterSkeleton(const Skeleton* skeleton); inline void RegisterSkeleton(const Skeleton* skeleton);
inline void RegisterVertexBuffer(const RenderBuffer* vertexBuffer); inline void RegisterVertexBuffer(const RenderBuffer* vertexBuffer);
@ -45,7 +45,7 @@ namespace Nz
private: private:
std::set<int> m_renderLayers; std::set<int> m_renderLayers;
robin_hood::unordered_map<int, std::size_t> m_renderLayerRegistry; robin_hood::unordered_map<int, std::size_t> m_renderLayerRegistry;
robin_hood::unordered_map<const MaterialPass*, std::size_t> m_materialPassRegistry; robin_hood::unordered_map<const MaterialInstance*, std::size_t> m_materialPassRegistry;
robin_hood::unordered_map<const RenderPipeline*, std::size_t> m_pipelineRegistry; robin_hood::unordered_map<const RenderPipeline*, std::size_t> m_pipelineRegistry;
robin_hood::unordered_map<const RenderBuffer*, std::size_t> m_vertexBufferRegistry; robin_hood::unordered_map<const RenderBuffer*, std::size_t> m_vertexBufferRegistry;
robin_hood::unordered_map<const Skeleton*, std::size_t> m_skeletonRegistry; robin_hood::unordered_map<const Skeleton*, std::size_t> m_skeletonRegistry;

View File

@ -26,7 +26,7 @@ namespace Nz
return it->second; return it->second;
} }
inline std::size_t RenderQueueRegistry::FetchMaterialPassIndex(const MaterialPass* materialPass) const inline std::size_t RenderQueueRegistry::FetchMaterialInstanceIndex(const MaterialInstance* materialPass) const
{ {
auto it = m_materialPassRegistry.find(materialPass); auto it = m_materialPassRegistry.find(materialPass);
assert(it != m_materialPassRegistry.end()); assert(it != m_materialPassRegistry.end());
@ -78,9 +78,9 @@ namespace Nz
m_renderLayers.insert(renderLayer); m_renderLayers.insert(renderLayer);
} }
inline void RenderQueueRegistry::RegisterMaterialPass(const MaterialPass* materialPass) inline void RenderQueueRegistry::RegisterMaterialInstance(const MaterialInstance* materialInstance)
{ {
m_materialPassRegistry.try_emplace(materialPass, m_materialPassRegistry.size()); m_materialPassRegistry.try_emplace(materialInstance, m_materialPassRegistry.size());
} }
inline void RenderQueueRegistry::RegisterPipeline(const RenderPipeline* pipeline) inline void RenderQueueRegistry::RegisterPipeline(const RenderPipeline* pipeline)

View File

@ -16,19 +16,19 @@
namespace Nz namespace Nz
{ {
class MaterialPass; class MaterialInstance;
class VertexDeclaration; class VertexDeclaration;
class ViewerInstance; class ViewerInstance;
class RenderSpriteChain : public RenderElement class RenderSpriteChain : public RenderElement
{ {
public: public:
inline RenderSpriteChain(int renderLayer, std::shared_ptr<MaterialPass> materialPass, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, std::shared_ptr<VertexDeclaration> vertexDeclaration, std::shared_ptr<Texture> textureOverlay, std::size_t spriteCount, const void* spriteData, const Recti& scissorBox); inline RenderSpriteChain(int renderLayer, std::shared_ptr<MaterialInstance> materialInstance, MaterialPassFlags materialFlags, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, std::shared_ptr<VertexDeclaration> vertexDeclaration, std::shared_ptr<Texture> textureOverlay, std::size_t spriteCount, const void* spriteData, const Recti& scissorBox);
~RenderSpriteChain() = default; ~RenderSpriteChain() = default;
inline UInt64 ComputeSortingScore(const Frustumf& frustum, const RenderQueueRegistry& registry) const override; inline UInt64 ComputeSortingScore(const Frustumf& frustum, const RenderQueueRegistry& registry) const override;
inline const MaterialPass& GetMaterialPass() const; inline const MaterialInstance& GetMaterialInstance() const;
inline const RenderPipeline& GetRenderPipeline() const; inline const RenderPipeline& GetRenderPipeline() const;
inline const Recti& GetScissorBox() const; inline const Recti& GetScissorBox() const;
inline std::size_t GetSpriteCount() const; inline std::size_t GetSpriteCount() const;
@ -42,13 +42,14 @@ namespace Nz
static constexpr BasicRenderElement ElementType = BasicRenderElement::SpriteChain; static constexpr BasicRenderElement ElementType = BasicRenderElement::SpriteChain;
private: private:
std::shared_ptr<MaterialPass> m_materialPass; std::shared_ptr<MaterialInstance> m_materialInstance;
std::shared_ptr<RenderPipeline> m_renderPipeline; std::shared_ptr<RenderPipeline> m_renderPipeline;
std::shared_ptr<VertexDeclaration> m_vertexDeclaration; std::shared_ptr<VertexDeclaration> m_vertexDeclaration;
std::shared_ptr<Texture> m_textureOverlay; std::shared_ptr<Texture> m_textureOverlay;
std::size_t m_spriteCount; std::size_t m_spriteCount;
const void* m_spriteData; const void* m_spriteData;
const WorldInstance& m_worldInstance; const WorldInstance& m_worldInstance;
MaterialPassFlags m_materialFlags;
Recti m_scissorBox; Recti m_scissorBox;
int m_renderLayer; int m_renderLayer;
}; };

View File

@ -9,15 +9,16 @@
namespace Nz namespace Nz
{ {
inline RenderSpriteChain::RenderSpriteChain(int renderLayer, std::shared_ptr<MaterialPass> materialPass, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, std::shared_ptr<VertexDeclaration> vertexDeclaration, std::shared_ptr<Texture> textureOverlay, std::size_t spriteCount, const void* spriteData, const Recti& scissorBox) : inline RenderSpriteChain::RenderSpriteChain(int renderLayer, std::shared_ptr<MaterialInstance> materialInstance, MaterialPassFlags materialFlags, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, std::shared_ptr<VertexDeclaration> vertexDeclaration, std::shared_ptr<Texture> textureOverlay, std::size_t spriteCount, const void* spriteData, const Recti& scissorBox) :
RenderElement(BasicRenderElement::SpriteChain), RenderElement(BasicRenderElement::SpriteChain),
m_materialPass(std::move(materialPass)), m_materialInstance(std::move(materialInstance)),
m_renderPipeline(std::move(renderPipeline)), m_renderPipeline(std::move(renderPipeline)),
m_vertexDeclaration(std::move(vertexDeclaration)), m_vertexDeclaration(std::move(vertexDeclaration)),
m_textureOverlay(std::move(textureOverlay)), m_textureOverlay(std::move(textureOverlay)),
m_spriteCount(spriteCount), m_spriteCount(spriteCount),
m_spriteData(spriteData), m_spriteData(spriteData),
m_worldInstance(worldInstance), m_worldInstance(worldInstance),
m_materialFlags(materialFlags),
m_scissorBox(scissorBox), m_scissorBox(scissorBox),
m_renderLayer(renderLayer) m_renderLayer(renderLayer)
{ {
@ -27,7 +28,7 @@ namespace Nz
{ {
UInt64 layerIndex = registry.FetchLayerIndex(m_renderLayer); UInt64 layerIndex = registry.FetchLayerIndex(m_renderLayer);
if (m_materialPass->IsFlagEnabled(MaterialPassFlag::SortByDistance)) if (m_materialFlags.Test(MaterialPassFlag::SortByDistance))
{ {
UInt64 matFlags = 1; UInt64 matFlags = 1;
@ -48,7 +49,7 @@ namespace Nz
else else
{ {
UInt64 elementType = GetElementType(); UInt64 elementType = GetElementType();
UInt64 materialPassIndex = registry.FetchMaterialPassIndex(m_materialPass.get()); UInt64 materialInstanceIndex = registry.FetchMaterialInstanceIndex(m_materialInstance.get());
UInt64 pipelineIndex = registry.FetchPipelineIndex(m_renderPipeline.get()); UInt64 pipelineIndex = registry.FetchPipelineIndex(m_renderPipeline.get());
UInt64 vertexDeclarationIndex = registry.FetchVertexDeclaration(m_vertexDeclaration.get()); UInt64 vertexDeclarationIndex = registry.FetchVertexDeclaration(m_vertexDeclaration.get());
@ -63,18 +64,18 @@ namespace Nz
// - VertexDeclaration (8bits) // - VertexDeclaration (8bits)
// - ?? (8bits) - Depth? // - ?? (8bits) - Depth?
return (layerIndex & 0xFF) << 60 | return (layerIndex & 0xFF) << 60 |
(matFlags) << 52 | (matFlags) << 52 |
(elementType & 0xF) << 51 | (elementType & 0xF) << 51 |
(pipelineIndex & 0xFFFF) << 35 | (pipelineIndex & 0xFFFF) << 35 |
(materialPassIndex & 0xFFFF) << 23 | (materialInstanceIndex & 0xFFFF) << 23 |
(vertexDeclarationIndex & 0xFF) << 7; (vertexDeclarationIndex & 0xFF) << 7;
} }
} }
inline const MaterialPass& RenderSpriteChain::GetMaterialPass() const inline const MaterialInstance& RenderSpriteChain::GetMaterialInstance() const
{ {
return *m_materialPass; return *m_materialInstance;
} }
inline const RenderPipeline& RenderSpriteChain::GetRenderPipeline() const inline const RenderPipeline& RenderSpriteChain::GetRenderPipeline() const
@ -115,7 +116,7 @@ namespace Nz
inline void RenderSpriteChain::Register(RenderQueueRegistry& registry) const inline void RenderSpriteChain::Register(RenderQueueRegistry& registry) const
{ {
registry.RegisterLayer(m_renderLayer); registry.RegisterLayer(m_renderLayer);
registry.RegisterMaterialPass(m_materialPass.get()); registry.RegisterMaterialInstance(m_materialInstance.get());
registry.RegisterPipeline(m_renderPipeline.get()); registry.RegisterPipeline(m_renderPipeline.get());
registry.RegisterVertexDeclaration(m_vertexDeclaration.get()); registry.RegisterVertexDeclaration(m_vertexDeclaration.get());
} }

View File

@ -17,14 +17,14 @@
namespace Nz namespace Nz
{ {
class MaterialPass; class MaterialInstance;
class RenderPipeline; class RenderPipeline;
class ShaderBinding; class ShaderBinding;
class RenderSubmesh : public RenderElement class RenderSubmesh : public RenderElement
{ {
public: public:
inline RenderSubmesh(int renderLayer, std::shared_ptr<MaterialPass> materialPass, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, const SkeletonInstance* skeletonInstance, std::size_t indexCount, IndexType indexType, std::shared_ptr<RenderBuffer> indexBuffer, std::shared_ptr<RenderBuffer> vertexBuffer, const Recti& scissorBox); inline RenderSubmesh(int renderLayer, std::shared_ptr<MaterialInstance> materialInstance, MaterialPassFlags materialFlags, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, const SkeletonInstance* skeletonInstance, std::size_t indexCount, IndexType indexType, std::shared_ptr<RenderBuffer> indexBuffer, std::shared_ptr<RenderBuffer> vertexBuffer, const Recti& scissorBox);
~RenderSubmesh() = default; ~RenderSubmesh() = default;
inline UInt64 ComputeSortingScore(const Frustumf& frustum, const RenderQueueRegistry& registry) const override; inline UInt64 ComputeSortingScore(const Frustumf& frustum, const RenderQueueRegistry& registry) const override;
@ -32,7 +32,7 @@ namespace Nz
inline const RenderBuffer* GetIndexBuffer() const; inline const RenderBuffer* GetIndexBuffer() const;
inline std::size_t GetIndexCount() const; inline std::size_t GetIndexCount() const;
inline IndexType GetIndexType() const; inline IndexType GetIndexType() const;
inline const MaterialPass& GetMaterialPass() const; inline const MaterialInstance& GetMaterialInstance() const;
inline const RenderPipeline* GetRenderPipeline() const; inline const RenderPipeline* GetRenderPipeline() const;
inline const Recti& GetScissorBox() const; inline const Recti& GetScissorBox() const;
inline const SkeletonInstance* GetSkeletonInstance() const; inline const SkeletonInstance* GetSkeletonInstance() const;
@ -46,12 +46,13 @@ namespace Nz
private: private:
std::shared_ptr<RenderBuffer> m_indexBuffer; std::shared_ptr<RenderBuffer> m_indexBuffer;
std::shared_ptr<RenderBuffer> m_vertexBuffer; std::shared_ptr<RenderBuffer> m_vertexBuffer;
std::shared_ptr<MaterialPass> m_materialPass; std::shared_ptr<MaterialInstance> m_materialInstance;
std::shared_ptr<RenderPipeline> m_renderPipeline; std::shared_ptr<RenderPipeline> m_renderPipeline;
std::size_t m_indexCount; std::size_t m_indexCount;
const SkeletonInstance* m_skeletonInstance; const SkeletonInstance* m_skeletonInstance;
const WorldInstance& m_worldInstance; const WorldInstance& m_worldInstance;
IndexType m_indexType; IndexType m_indexType;
MaterialPassFlags m_materialFlags;
Recti m_scissorBox; Recti m_scissorBox;
int m_renderLayer; int m_renderLayer;
}; };

View File

@ -9,16 +9,17 @@
namespace Nz namespace Nz
{ {
inline RenderSubmesh::RenderSubmesh(int renderLayer, std::shared_ptr<MaterialPass> materialPass, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, const SkeletonInstance* skeletonInstance, std::size_t indexCount, IndexType indexType, std::shared_ptr<RenderBuffer> indexBuffer, std::shared_ptr<RenderBuffer> vertexBuffer, const Recti& scissorBox) : inline RenderSubmesh::RenderSubmesh(int renderLayer, std::shared_ptr<MaterialInstance> materialInstance, MaterialPassFlags materialFlags, std::shared_ptr<RenderPipeline> renderPipeline, const WorldInstance& worldInstance, const SkeletonInstance* skeletonInstance, std::size_t indexCount, IndexType indexType, std::shared_ptr<RenderBuffer> indexBuffer, std::shared_ptr<RenderBuffer> vertexBuffer, const Recti& scissorBox) :
RenderElement(BasicRenderElement::Submesh), RenderElement(BasicRenderElement::Submesh),
m_indexBuffer(std::move(indexBuffer)), m_indexBuffer(std::move(indexBuffer)),
m_vertexBuffer(std::move(vertexBuffer)), m_vertexBuffer(std::move(vertexBuffer)),
m_materialPass(std::move(materialPass)), m_materialInstance(std::move(materialInstance)),
m_renderPipeline(std::move(renderPipeline)), m_renderPipeline(std::move(renderPipeline)),
m_indexCount(indexCount), m_indexCount(indexCount),
m_skeletonInstance(skeletonInstance), m_skeletonInstance(skeletonInstance),
m_worldInstance(worldInstance), m_worldInstance(worldInstance),
m_indexType(indexType), m_indexType(indexType),
m_materialFlags(materialFlags),
m_scissorBox(scissorBox), m_scissorBox(scissorBox),
m_renderLayer(renderLayer) m_renderLayer(renderLayer)
{ {
@ -27,8 +28,8 @@ namespace Nz
inline UInt64 RenderSubmesh::ComputeSortingScore(const Frustumf& frustum, const RenderQueueRegistry& registry) const inline UInt64 RenderSubmesh::ComputeSortingScore(const Frustumf& frustum, const RenderQueueRegistry& registry) const
{ {
UInt64 layerIndex = registry.FetchLayerIndex(m_renderLayer); UInt64 layerIndex = registry.FetchLayerIndex(m_renderLayer);
if (m_materialPass->IsFlagEnabled(MaterialPassFlag::SortByDistance)) if (m_materialFlags.Test(MaterialPassFlag::SortByDistance))
{ {
UInt64 matFlags = 1; UInt64 matFlags = 1;
@ -48,7 +49,7 @@ namespace Nz
else else
{ {
UInt64 elementType = GetElementType(); UInt64 elementType = GetElementType();
UInt64 materialPassIndex = registry.FetchMaterialPassIndex(m_materialPass.get()); UInt64 materialInstanceIndex = registry.FetchMaterialInstanceIndex(m_materialInstance.get());
UInt64 pipelineIndex = registry.FetchPipelineIndex(m_renderPipeline.get()); UInt64 pipelineIndex = registry.FetchPipelineIndex(m_renderPipeline.get());
UInt64 vertexBufferIndex = registry.FetchVertexBuffer(m_vertexBuffer.get()); UInt64 vertexBufferIndex = registry.FetchVertexBuffer(m_vertexBuffer.get());
@ -67,12 +68,12 @@ namespace Nz
// - VertexBuffer (8bits) // - VertexBuffer (8bits)
// - Skeleton (8bits) // - Skeleton (8bits)
return (layerIndex & 0xFF) << 60 | return (layerIndex & 0xFF) << 60 |
(matFlags) << 52 | (matFlags) << 52 |
(elementType & 0xF) << 51 | (elementType & 0xF) << 51 |
(pipelineIndex & 0xFFFF) << 35 | (pipelineIndex & 0xFFFF) << 35 |
(materialPassIndex & 0xFFFF) << 23 | (materialInstanceIndex & 0xFFFF) << 23 |
(vertexBufferIndex & 0xFF) << 7 | (vertexBufferIndex & 0xFF) << 7 |
(skeletonIndex & 0xFF); (skeletonIndex & 0xFF);
} }
} }
@ -92,9 +93,9 @@ namespace Nz
return m_indexType; return m_indexType;
} }
inline const MaterialPass& RenderSubmesh::GetMaterialPass() const inline const MaterialInstance& RenderSubmesh::GetMaterialInstance() const
{ {
return *m_materialPass; return *m_materialInstance;
} }
inline const RenderPipeline* RenderSubmesh::GetRenderPipeline() const inline const RenderPipeline* RenderSubmesh::GetRenderPipeline() const
@ -125,7 +126,7 @@ namespace Nz
inline void RenderSubmesh::Register(RenderQueueRegistry& registry) const inline void RenderSubmesh::Register(RenderQueueRegistry& registry) const
{ {
registry.RegisterLayer(m_renderLayer); registry.RegisterLayer(m_renderLayer);
registry.RegisterMaterialPass(m_materialPass.get()); registry.RegisterMaterialInstance(m_materialInstance.get());
registry.RegisterPipeline(m_renderPipeline.get()); registry.RegisterPipeline(m_renderPipeline.get());
registry.RegisterVertexBuffer(m_vertexBuffer.get()); registry.RegisterVertexBuffer(m_vertexBuffer.get());
if (m_skeletonInstance) if (m_skeletonInstance)

View File

@ -0,0 +1,108 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_SHADERREFLECTION_HPP
#define NAZARA_GRAPHICS_SHADERREFLECTION_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Renderer/RenderPipelineLayout.hpp>
#include <NZSL/Ast/Module.hpp>
#include <NZSL/Ast/RecursiveVisitor.hpp>
#include <NZSL/Math/FieldOffsets.hpp>
#include <unordered_map>
namespace Nz
{
class NAZARA_GRAPHICS_API ShaderReflection : nzsl::Ast::RecursiveVisitor
{
public:
struct ExternalBlockData;
struct OptionData;
struct StructData;
ShaderReflection() = default;
ShaderReflection(const ShaderReflection&) = delete;
ShaderReflection(ShaderReflection&&) = delete;
~ShaderReflection() = default;
inline const RenderPipelineLayoutInfo& GetPipelineLayoutInfo() const;
inline const ExternalBlockData* GetExternalBlockByTag(const std::string& tag) const;
inline const OptionData* GetOptionByName(const std::string& optionName) const;
inline const StructData* GetStructByIndex(std::size_t structIndex) const;
void Reflect(nzsl::Ast::Module& module);
ShaderReflection& operator=(const ShaderReflection&) = delete;
ShaderReflection& operator=(ShaderReflection&&) = delete;
struct ExternalData
{
UInt32 bindingSet;
UInt32 bindingIndex;
};
struct ExternalStorageBlock : ExternalData
{
std::size_t structIndex;
};
struct ExternalTexture : ExternalData
{
nzsl::ImageType imageType;
nzsl::Ast::PrimitiveType sampledType;
};
struct ExternalUniformBlock : ExternalData
{
std::size_t structIndex;
};
struct ExternalBlockData
{
std::unordered_map<std::string /*tag*/, ExternalStorageBlock> storageBlocks;
std::unordered_map<std::string /*tag*/, ExternalTexture> samplers;
std::unordered_map<std::string /*tag*/, ExternalUniformBlock> uniformBlocks;
};
struct OptionData
{
nzsl::Ast::ExpressionType type;
UInt32 hash;
};
struct StructMemberData
{
std::size_t offset;
std::size_t size;
nzsl::Ast::ExpressionType type;
};
struct StructData
{
StructData(nzsl::StructLayout layout) : fieldOffsets(layout) {}
std::unordered_map<std::string /*tag*/, StructMemberData> members;
nzsl::FieldOffsets fieldOffsets;
};
private:
void Visit(nzsl::Ast::ConditionalStatement& node) override;
void Visit(nzsl::Ast::DeclareExternalStatement& node) override;
void Visit(nzsl::Ast::DeclareOptionStatement& node) override;
void Visit(nzsl::Ast::DeclareStructStatement& node) override;
std::unordered_map<std::string /*tag*/, ExternalBlockData> m_externalBlocks;
std::unordered_map<std::string /*name*/, OptionData> m_options;
std::unordered_map<std::size_t /*structIndex*/, StructData> m_structs;
RenderPipelineLayoutInfo m_pipelineLayoutInfo;
bool m_isConditional;
};
}
#include <Nazara/Graphics/ShaderReflection.inl>
#endif // NAZARA_GRAPHICS_SHADERREFLECTION_HPP

View File

@ -0,0 +1,43 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/ShaderReflection.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
inline const RenderPipelineLayoutInfo& ShaderReflection::GetPipelineLayoutInfo() const
{
return m_pipelineLayoutInfo;
}
inline auto ShaderReflection::GetExternalBlockByTag(const std::string& tag) const -> const ExternalBlockData*
{
auto it = m_externalBlocks.find(tag);
if (it == m_externalBlocks.end())
return nullptr;
return &it->second;
}
inline auto ShaderReflection::GetOptionByName(const std::string& optionName) const -> const OptionData*
{
auto it = m_options.find(optionName);
if (it == m_options.end())
return nullptr;
return &it->second;
}
inline auto ShaderReflection::GetStructByIndex(std::size_t structIndex) const -> const StructData*
{
auto it = m_structs.find(structIndex);
if (it == m_structs.end())
return nullptr;
return &it->second;
}
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -9,6 +9,7 @@
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Math/Matrix4.hpp> #include <Nazara/Math/Matrix4.hpp>
#include <Nazara/Renderer/ShaderBinding.hpp> #include <Nazara/Renderer/ShaderBinding.hpp>
#include <Nazara/Utility/Skeleton.hpp> #include <Nazara/Utility/Skeleton.hpp>
@ -23,7 +24,7 @@ namespace Nz
using SkeletonInstancePtr = std::shared_ptr<SkeletonInstance>; using SkeletonInstancePtr = std::shared_ptr<SkeletonInstance>;
class NAZARA_GRAPHICS_API SkeletonInstance class NAZARA_GRAPHICS_API SkeletonInstance : public TransferInterface
{ {
public: public:
SkeletonInstance(std::shared_ptr<const Skeleton> skeleton); SkeletonInstance(std::shared_ptr<const Skeleton> skeleton);
@ -35,7 +36,7 @@ namespace Nz
inline const std::shared_ptr<RenderBuffer>& GetSkeletalBuffer() const; inline const std::shared_ptr<RenderBuffer>& GetSkeletalBuffer() const;
inline const std::shared_ptr<const Skeleton>& GetSkeleton() const; inline const std::shared_ptr<const Skeleton>& GetSkeleton() const;
void UpdateBuffers(UploadPool& uploadPool, CommandBufferBuilder& builder); void OnTransfer(RenderFrame& renderFrame, CommandBufferBuilder& builder) override;
SkeletonInstance& operator=(const SkeletonInstance&) = delete; SkeletonInstance& operator=(const SkeletonInstance&) = delete;
SkeletonInstance& operator=(SkeletonInstance&& skeletonInstance) noexcept; SkeletonInstance& operator=(SkeletonInstance&& skeletonInstance) noexcept;

View File

@ -22,7 +22,7 @@ namespace Nz
public: public:
struct Corner; struct Corner;
SlicedSprite(std::shared_ptr<Material> material); SlicedSprite(std::shared_ptr<MaterialInstance> material);
SlicedSprite(const SlicedSprite&) = delete; SlicedSprite(const SlicedSprite&) = delete;
SlicedSprite(SlicedSprite&&) noexcept = default; SlicedSprite(SlicedSprite&&) noexcept = default;
~SlicedSprite() = default; ~SlicedSprite() = default;
@ -31,7 +31,7 @@ namespace Nz
inline const Color& GetColor() const; inline const Color& GetColor() const;
inline const Corner& GetBottomRightCorner() const; inline const Corner& GetBottomRightCorner() const;
const std::shared_ptr<Material>& GetMaterial(std::size_t i = 0) const override; const std::shared_ptr<MaterialInstance>& GetMaterial(std::size_t i = 0) const override;
std::size_t GetMaterialCount() const override; std::size_t GetMaterialCount() const override;
inline const Corner& GetTopLeftCorner() const; inline const Corner& GetTopLeftCorner() const;
inline const Rectf& GetTextureCoords() const; inline const Rectf& GetTextureCoords() const;
@ -41,7 +41,7 @@ namespace Nz
inline void SetCorners(const Corner& topLeftCorner, const Corner& bottomRightCorner); inline void SetCorners(const Corner& topLeftCorner, const Corner& bottomRightCorner);
inline void SetCornersSize(const Vector2f& topLeftSize, const Vector2f& bottomRightSize); inline void SetCornersSize(const Vector2f& topLeftSize, const Vector2f& bottomRightSize);
inline void SetCornersTextureCoords(const Vector2f& topLeftTextureCoords, const Vector2f& bottomRightTextureCoords); inline void SetCornersTextureCoords(const Vector2f& topLeftTextureCoords, const Vector2f& bottomRightTextureCoords);
inline void SetMaterial(std::shared_ptr<Material> material); inline void SetMaterial(std::shared_ptr<MaterialInstance> material);
inline void SetSize(const Vector2f& size); inline void SetSize(const Vector2f& size);
inline void SetTextureCoords(const Rectf& textureCoords); inline void SetTextureCoords(const Rectf& textureCoords);
inline void SetTextureRect(const Rectf& textureRect); inline void SetTextureRect(const Rectf& textureRect);
@ -59,7 +59,7 @@ namespace Nz
void UpdateVertices(); void UpdateVertices();
std::array<VertexStruct_XYZ_Color_UV, 4 * 9> m_vertices; std::array<VertexStruct_XYZ_Color_UV, 4 * 9> m_vertices;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::size_t m_spriteCount; std::size_t m_spriteCount;
Color m_color; Color m_color;
Corner m_topLeftCorner; Corner m_topLeftCorner;

View File

@ -59,7 +59,7 @@ namespace Nz
UpdateVertices(); UpdateVertices();
} }
inline void SlicedSprite::SetMaterial(std::shared_ptr<Material> material) inline void SlicedSprite::SetMaterial(std::shared_ptr<MaterialInstance> material)
{ {
assert(material); assert(material);

View File

@ -20,7 +20,7 @@ namespace Nz
class NAZARA_GRAPHICS_API Sprite : public InstancedRenderable class NAZARA_GRAPHICS_API Sprite : public InstancedRenderable
{ {
public: public:
Sprite(std::shared_ptr<Material> material); Sprite(std::shared_ptr<MaterialInstance> material);
Sprite(const Sprite&) = delete; Sprite(const Sprite&) = delete;
Sprite(Sprite&&) noexcept = default; Sprite(Sprite&&) noexcept = default;
~Sprite() = default; ~Sprite() = default;
@ -29,7 +29,7 @@ namespace Nz
inline const Color& GetColor() const; inline const Color& GetColor() const;
inline const Color& GetCornerColor(RectCorner corner) const; inline const Color& GetCornerColor(RectCorner corner) const;
const std::shared_ptr<Material>& GetMaterial(std::size_t i = 0) const override; const std::shared_ptr<MaterialInstance>& GetMaterial(std::size_t i = 0) const override;
std::size_t GetMaterialCount() const override; std::size_t GetMaterialCount() const override;
inline const Vector3f& GetOrigin() const; inline const Vector3f& GetOrigin() const;
inline const Vector2f& GetSize() const; inline const Vector2f& GetSize() const;
@ -38,7 +38,7 @@ namespace Nz
inline void SetColor(const Color& color); inline void SetColor(const Color& color);
inline void SetCornerColor(RectCorner corner, const Color& color); inline void SetCornerColor(RectCorner corner, const Color& color);
inline void SetMaterial(std::shared_ptr<Material> material); inline void SetMaterial(std::shared_ptr<MaterialInstance> material);
inline void SetOrigin(const Vector3f& origin); inline void SetOrigin(const Vector3f& origin);
inline void SetSize(const Vector2f& size); inline void SetSize(const Vector2f& size);
inline void SetTextureCoords(const Rectf& textureCoords); inline void SetTextureCoords(const Rectf& textureCoords);
@ -52,7 +52,7 @@ namespace Nz
std::array<Color, RectCornerCount> m_cornerColor; std::array<Color, RectCornerCount> m_cornerColor;
std::array<VertexStruct_XYZ_Color_UV, 4> m_vertices; std::array<VertexStruct_XYZ_Color_UV, 4> m_vertices;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
Color m_color; Color m_color;
Rectf m_textureCoords; Rectf m_textureCoords;
Vector2f m_size; Vector2f m_size;

View File

@ -47,7 +47,7 @@ namespace Nz
UpdateVertices(); UpdateVertices();
} }
inline void Sprite::SetMaterial(std::shared_ptr<Material> material) inline void Sprite::SetMaterial(std::shared_ptr<MaterialInstance> material)
{ {
assert(material); assert(material);

View File

@ -19,7 +19,6 @@
namespace Nz namespace Nz
{ {
class MaterialPass;
class RenderDevice; class RenderDevice;
class RenderPipeline; class RenderPipeline;
class ShaderBinding; class ShaderBinding;
@ -85,7 +84,7 @@ namespace Nz
UInt8* currentAllocationMemPtr = nullptr; UInt8* currentAllocationMemPtr = nullptr;
const VertexDeclaration* currentVertexDeclaration = nullptr; const VertexDeclaration* currentVertexDeclaration = nullptr;
RenderBuffer* currentVertexBuffer = nullptr; RenderBuffer* currentVertexBuffer = nullptr;
const MaterialPass* currentMaterialPass = nullptr; const MaterialInstance* currentMaterialInstance = nullptr;
const RenderPipeline* currentPipeline = nullptr; const RenderPipeline* currentPipeline = nullptr;
const ShaderBinding* currentShaderBinding = nullptr; const ShaderBinding* currentShaderBinding = nullptr;
const Texture* currentTextureOverlay = nullptr; const Texture* currentTextureOverlay = nullptr;

View File

@ -23,7 +23,7 @@ namespace Nz
class NAZARA_GRAPHICS_API TextSprite : public InstancedRenderable class NAZARA_GRAPHICS_API TextSprite : public InstancedRenderable
{ {
public: public:
TextSprite(std::shared_ptr<Material> material); TextSprite(std::shared_ptr<MaterialInstance> material = {});
TextSprite(const TextSprite&) = delete; TextSprite(const TextSprite&) = delete;
TextSprite(TextSprite&&) noexcept = default; TextSprite(TextSprite&&) noexcept = default;
~TextSprite() = default; ~TextSprite() = default;
@ -32,10 +32,10 @@ namespace Nz
inline void Clear(); inline void Clear();
const std::shared_ptr<Material>& GetMaterial(std::size_t i = 0) const override; const std::shared_ptr<MaterialInstance>& GetMaterial(std::size_t i = 0) const override;
std::size_t GetMaterialCount() const override; std::size_t GetMaterialCount() const override;
inline void SetMaterial(std::shared_ptr<Material> material); inline void SetMaterial(std::shared_ptr<MaterialInstance> material);
void Update(const AbstractTextDrawer& drawer, float scale = 1.f); void Update(const AbstractTextDrawer& drawer, float scale = 1.f);
@ -92,7 +92,7 @@ namespace Nz
std::unordered_map<const AbstractAtlas*, AtlasSlots> m_atlases; std::unordered_map<const AbstractAtlas*, AtlasSlots> m_atlases;
mutable std::unordered_map<RenderKey, RenderIndices, HashRenderKey> m_renderInfos; mutable std::unordered_map<RenderKey, RenderIndices, HashRenderKey> m_renderInfos;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::vector<RenderData> m_data; std::vector<RenderData> m_data;
std::vector<VertexStruct_XYZ_Color_UV> m_vertices; std::vector<VertexStruct_XYZ_Color_UV> m_vertices;
Recti m_scissorBox; Recti m_scissorBox;

View File

@ -15,7 +15,7 @@ namespace Nz
OnElementInvalidated(this); OnElementInvalidated(this);
} }
inline void TextSprite::SetMaterial(std::shared_ptr<Material> material) inline void TextSprite::SetMaterial(std::shared_ptr<MaterialInstance> material)
{ {
assert(material); assert(material);

View File

@ -0,0 +1,38 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#pragma once
#ifndef NAZARA_GRAPHICS_TRANSFERINTERFACE_HPP
#define NAZARA_GRAPHICS_TRANSFERINTERFACE_HPP
#include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp>
#include <Nazara/Utils/Signal.hpp>
namespace Nz
{
class CommandBufferBuilder;
class RenderFrame;
class NAZARA_GRAPHICS_API TransferInterface
{
public:
TransferInterface() = default;
TransferInterface(const TransferInterface&) = default;
TransferInterface(TransferInterface&&) = default;
virtual ~TransferInterface();
virtual void OnTransfer(RenderFrame& renderFrame, CommandBufferBuilder& builder) = 0;
TransferInterface& operator=(const TransferInterface&) = default;
TransferInterface& operator=(TransferInterface&&) = default;
NazaraSignal(OnTransferRequired, TransferInterface* /*transfer*/);
};
}
#include <Nazara/Graphics/TransferInterface.inl>
#endif // NAZARA_GRAPHICS_TRANSFERINTERFACE_HPP

View File

@ -0,0 +1,12 @@
// Copyright (C) 2022 Jérôme "Lynix" Leclercq (lynix680@gmail.com)
// This file is part of the "Nazara Engine - Graphics module"
// For conditions of distribution and use, see copyright notice in Config.hpp
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Graphics/Debug.hpp>
namespace Nz
{
}
#include <Nazara/Graphics/DebugOff.hpp>

View File

@ -9,6 +9,7 @@
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Math/Matrix4.hpp> #include <Nazara/Math/Matrix4.hpp>
#include <Nazara/Renderer/ShaderBinding.hpp> #include <Nazara/Renderer/ShaderBinding.hpp>
#include <memory> #include <memory>
@ -20,7 +21,7 @@ namespace Nz
class RenderBuffer; class RenderBuffer;
class UploadPool; class UploadPool;
class NAZARA_GRAPHICS_API ViewerInstance class NAZARA_GRAPHICS_API ViewerInstance : public TransferInterface
{ {
public: public:
ViewerInstance(); ViewerInstance();
@ -39,7 +40,8 @@ namespace Nz
inline std::shared_ptr<RenderBuffer>& GetViewerBuffer(); inline std::shared_ptr<RenderBuffer>& GetViewerBuffer();
inline const std::shared_ptr<RenderBuffer>& GetViewerBuffer() const; inline const std::shared_ptr<RenderBuffer>& GetViewerBuffer() const;
void UpdateBuffers(UploadPool& uploadPool, CommandBufferBuilder& builder); void OnTransfer(RenderFrame& renderFrame, CommandBufferBuilder& builder) override;
inline void UpdateEyePosition(const Vector3f& eyePosition); inline void UpdateEyePosition(const Vector3f& eyePosition);
inline void UpdateProjectionMatrix(const Matrix4f& projectionMatrix); inline void UpdateProjectionMatrix(const Matrix4f& projectionMatrix);
inline void UpdateProjectionMatrix(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix); inline void UpdateProjectionMatrix(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix);
@ -54,6 +56,8 @@ namespace Nz
ViewerInstance& operator=(ViewerInstance&&) noexcept = default; ViewerInstance& operator=(ViewerInstance&&) noexcept = default;
private: private:
inline void InvalidateData();
std::shared_ptr<RenderBuffer> m_viewerDataBuffer; std::shared_ptr<RenderBuffer> m_viewerDataBuffer;
Matrix4f m_invProjectionMatrix; Matrix4f m_invProjectionMatrix;
Matrix4f m_invViewProjMatrix; Matrix4f m_invViewProjMatrix;

View File

@ -61,7 +61,8 @@ namespace Nz
inline void ViewerInstance::UpdateEyePosition(const Vector3f& eyePosition) inline void ViewerInstance::UpdateEyePosition(const Vector3f& eyePosition)
{ {
m_eyePosition = eyePosition; m_eyePosition = eyePosition;
m_dataInvalidated = true;
InvalidateData();
} }
inline void ViewerInstance::UpdateProjectionMatrix(const Matrix4f& projectionMatrix) inline void ViewerInstance::UpdateProjectionMatrix(const Matrix4f& projectionMatrix)
@ -73,7 +74,7 @@ namespace Nz
m_viewProjMatrix = m_viewMatrix * m_projectionMatrix; m_viewProjMatrix = m_viewMatrix * m_projectionMatrix;
m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix; m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateProjectionMatrix(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix) inline void ViewerInstance::UpdateProjectionMatrix(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix)
@ -84,7 +85,7 @@ namespace Nz
m_viewProjMatrix = m_viewMatrix * m_projectionMatrix; m_viewProjMatrix = m_viewMatrix * m_projectionMatrix;
m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix; m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateProjViewMatrices(const Matrix4f& projectionMatrix, const Matrix4f& viewMatrix) inline void ViewerInstance::UpdateProjViewMatrices(const Matrix4f& projectionMatrix, const Matrix4f& viewMatrix)
@ -100,7 +101,7 @@ namespace Nz
m_viewProjMatrix = m_viewMatrix * m_projectionMatrix; m_viewProjMatrix = m_viewMatrix * m_projectionMatrix;
m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix; m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateProjViewMatrices(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix, const Matrix4f& viewMatrix, const Matrix4f& invViewMatrix) inline void ViewerInstance::UpdateProjViewMatrices(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix, const Matrix4f& viewMatrix, const Matrix4f& invViewMatrix)
@ -113,7 +114,7 @@ namespace Nz
m_viewProjMatrix = m_viewMatrix * m_projectionMatrix; m_viewProjMatrix = m_viewMatrix * m_projectionMatrix;
m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix; m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateProjViewMatrices(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix, const Matrix4f& viewMatrix, const Matrix4f& invViewMatrix, const Matrix4f& viewProjMatrix, const Matrix4f& invViewProjMatrix) inline void ViewerInstance::UpdateProjViewMatrices(const Matrix4f& projectionMatrix, const Matrix4f& invProjectionMatrix, const Matrix4f& viewMatrix, const Matrix4f& invViewMatrix, const Matrix4f& viewProjMatrix, const Matrix4f& invViewProjMatrix)
@ -126,14 +127,14 @@ namespace Nz
m_viewProjMatrix = viewProjMatrix; m_viewProjMatrix = viewProjMatrix;
m_invViewProjMatrix = invViewProjMatrix; m_invViewProjMatrix = invViewProjMatrix;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateTargetSize(const Vector2f& targetSize) inline void ViewerInstance::UpdateTargetSize(const Vector2f& targetSize)
{ {
m_targetSize = targetSize; m_targetSize = targetSize;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateViewMatrix(const Matrix4f& viewMatrix) inline void ViewerInstance::UpdateViewMatrix(const Matrix4f& viewMatrix)
@ -145,7 +146,7 @@ namespace Nz
m_viewProjMatrix = m_viewMatrix * m_projectionMatrix; m_viewProjMatrix = m_viewMatrix * m_projectionMatrix;
m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix; m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix;
m_dataInvalidated = true; InvalidateData();
} }
inline void ViewerInstance::UpdateViewMatrix(const Matrix4f& viewMatrix, const Matrix4f& invViewMatrix) inline void ViewerInstance::UpdateViewMatrix(const Matrix4f& viewMatrix, const Matrix4f& invViewMatrix)
@ -156,7 +157,13 @@ namespace Nz
m_viewProjMatrix = m_viewMatrix * m_projectionMatrix; m_viewProjMatrix = m_viewMatrix * m_projectionMatrix;
m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix; m_invViewProjMatrix = m_invProjectionMatrix * m_invViewMatrix;
InvalidateData();
}
inline void ViewerInstance::InvalidateData()
{
m_dataInvalidated = true; m_dataInvalidated = true;
OnTransferRequired(this);
} }
} }

View File

@ -9,6 +9,7 @@
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Graphics/Config.hpp> #include <Nazara/Graphics/Config.hpp>
#include <Nazara/Graphics/TransferInterface.hpp>
#include <Nazara/Math/Matrix4.hpp> #include <Nazara/Math/Matrix4.hpp>
#include <Nazara/Renderer/ShaderBinding.hpp> #include <Nazara/Renderer/ShaderBinding.hpp>
#include <memory> #include <memory>
@ -22,7 +23,7 @@ namespace Nz
using WorldInstancePtr = std::shared_ptr<WorldInstance>; using WorldInstancePtr = std::shared_ptr<WorldInstance>;
class NAZARA_GRAPHICS_API WorldInstance class NAZARA_GRAPHICS_API WorldInstance : public TransferInterface
{ {
public: public:
WorldInstance(); WorldInstance();
@ -35,7 +36,8 @@ namespace Nz
inline const Matrix4f& GetInvWorldMatrix() const; inline const Matrix4f& GetInvWorldMatrix() const;
inline const Matrix4f& GetWorldMatrix() const; inline const Matrix4f& GetWorldMatrix() const;
void UpdateBuffers(UploadPool& uploadPool, CommandBufferBuilder& builder); void OnTransfer(RenderFrame& renderFrame, CommandBufferBuilder& builder) override;
inline void UpdateWorldMatrix(const Matrix4f& worldMatrix); inline void UpdateWorldMatrix(const Matrix4f& worldMatrix);
inline void UpdateWorldMatrix(const Matrix4f& worldMatrix, const Matrix4f& invWorldMatrix); inline void UpdateWorldMatrix(const Matrix4f& worldMatrix, const Matrix4f& invWorldMatrix);
@ -43,6 +45,8 @@ namespace Nz
WorldInstance& operator=(WorldInstance&&) noexcept = default; WorldInstance& operator=(WorldInstance&&) noexcept = default;
private: private:
inline void InvalidateData();
std::shared_ptr<RenderBuffer> m_instanceDataBuffer; std::shared_ptr<RenderBuffer> m_instanceDataBuffer;
Matrix4f m_invWorldMatrix; Matrix4f m_invWorldMatrix;
Matrix4f m_worldMatrix; Matrix4f m_worldMatrix;

View File

@ -34,14 +34,21 @@ namespace Nz
if (!m_worldMatrix.GetInverseTransform(&m_invWorldMatrix)) if (!m_worldMatrix.GetInverseTransform(&m_invWorldMatrix))
NazaraError("failed to inverse world matrix"); NazaraError("failed to inverse world matrix");
m_dataInvalided = true; InvalidateData();
} }
inline void WorldInstance::UpdateWorldMatrix(const Matrix4f& worldMatrix, const Matrix4f& invWorldMatrix) inline void WorldInstance::UpdateWorldMatrix(const Matrix4f& worldMatrix, const Matrix4f& invWorldMatrix)
{ {
m_worldMatrix = worldMatrix; m_worldMatrix = worldMatrix;
m_invWorldMatrix = invWorldMatrix; m_invWorldMatrix = invWorldMatrix;
InvalidateData();
}
void WorldInstance::InvalidateData()
{
m_dataInvalided = true; m_dataInvalided = true;
OnTransferRequired(this);
} }
} }

View File

@ -19,7 +19,7 @@ namespace Nz
class RenderPass; class RenderPass;
class Texture; class Texture;
class NAZARA_OPENGLRENDERER_API OpenGLFboFramebuffer : public OpenGLFramebuffer class NAZARA_OPENGLRENDERER_API OpenGLFboFramebuffer final : public OpenGLFramebuffer
{ {
public: public:
OpenGLFboFramebuffer(OpenGLDevice& device, const std::vector<std::shared_ptr<Texture>>& attachments); OpenGLFboFramebuffer(OpenGLDevice& device, const std::vector<std::shared_ptr<Texture>>& attachments);
@ -31,12 +31,15 @@ namespace Nz
std::size_t GetColorBufferCount() const override; std::size_t GetColorBufferCount() const override;
const Vector2ui& GetSize() const override;
OpenGLFboFramebuffer& operator=(const OpenGLFboFramebuffer&) = delete; OpenGLFboFramebuffer& operator=(const OpenGLFboFramebuffer&) = delete;
OpenGLFboFramebuffer& operator=(OpenGLFboFramebuffer&&) = delete; OpenGLFboFramebuffer& operator=(OpenGLFboFramebuffer&&) = delete;
private: private:
GL::Framebuffer m_framebuffer; GL::Framebuffer m_framebuffer;
std::size_t m_colorAttachmentCount; std::size_t m_colorAttachmentCount;
Vector2ui m_size;
}; };
} }

View File

@ -8,6 +8,7 @@
#define NAZARA_OPENGLRENDERER_OPENGLFRAMEBUFFER_HPP #define NAZARA_OPENGLRENDERER_OPENGLFRAMEBUFFER_HPP
#include <Nazara/Prerequisites.hpp> #include <Nazara/Prerequisites.hpp>
#include <Nazara/Math/Vector2.hpp>
#include <Nazara/OpenGLRenderer/Config.hpp> #include <Nazara/OpenGLRenderer/Config.hpp>
#include <Nazara/Renderer/Framebuffer.hpp> #include <Nazara/Renderer/Framebuffer.hpp>
@ -26,6 +27,8 @@ namespace Nz
virtual std::size_t GetColorBufferCount() const = 0; virtual std::size_t GetColorBufferCount() const = 0;
virtual const Vector2ui& GetSize() const = 0;
OpenGLFramebuffer& operator=(const OpenGLFramebuffer&) = delete; OpenGLFramebuffer& operator=(const OpenGLFramebuffer&) = delete;
OpenGLFramebuffer& operator=(OpenGLFramebuffer&&) noexcept = default; OpenGLFramebuffer& operator=(OpenGLFramebuffer&&) noexcept = default;
}; };

View File

@ -22,7 +22,7 @@ namespace Nz
{ {
class RenderWindow; class RenderWindow;
class NAZARA_OPENGLRENDERER_API OpenGLRenderWindow : public RenderWindowImpl class NAZARA_OPENGLRENDERER_API OpenGLRenderWindow final : public RenderWindowImpl
{ {
public: public:
OpenGLRenderWindow(RenderWindow& owner); OpenGLRenderWindow(RenderWindow& owner);

View File

@ -26,6 +26,8 @@ namespace Nz
std::size_t GetColorBufferCount() const override; std::size_t GetColorBufferCount() const override;
const Vector2ui& GetSize() const override;
OpenGLWindowFramebuffer& operator=(const OpenGLWindowFramebuffer&) = delete; OpenGLWindowFramebuffer& operator=(const OpenGLWindowFramebuffer&) = delete;
OpenGLWindowFramebuffer& operator=(OpenGLWindowFramebuffer&&) = delete; OpenGLWindowFramebuffer& operator=(OpenGLWindowFramebuffer&&) = delete;

View File

@ -111,10 +111,10 @@ namespace Nz::GL
inline void Context::ResetColorWriteMasks() const inline void Context::ResetColorWriteMasks() const
{ {
if (!m_state.renderStates.colorWrite) if (m_state.renderStates.colorWriteMask != ColorComponentAll)
{ {
glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE); glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
m_state.renderStates.colorWrite = true; m_state.renderStates.colorWriteMask = ColorComponentAll;
} }
} }

View File

@ -23,6 +23,9 @@
typedef void (GL_APIENTRYP PFNGLDRAWBUFFERPROC) (GLenum buf); typedef void (GL_APIENTRYP PFNGLDRAWBUFFERPROC) (GLenum buf);
typedef void (GL_APIENTRYP PFNGLPOLYGONMODEPROC) (GLenum face, GLenum mode); typedef void (GL_APIENTRYP PFNGLPOLYGONMODEPROC) (GLenum face, GLenum mode);
// Depth clamp (OpenGL 3.2)
#define GL_DEPTH_CLAMP 0x864F
// Clip control (OpenGL 4.5) // Clip control (OpenGL 4.5)
#define GL_LOWER_LEFT 0x8CA1 #define GL_LOWER_LEFT 0x8CA1
#define GL_UPPER_LEFT 0x8CA2 #define GL_UPPER_LEFT 0x8CA2

View File

@ -24,6 +24,24 @@ namespace Nz
Store Store
}; };
enum class ColorComponent
{
Red,
Green,
Blue,
Alpha
};
template<>
struct EnumAsFlags<ColorComponent>
{
static constexpr ColorComponent max = ColorComponent::Alpha;
};
using ColorComponentMask = Flags<ColorComponent>;
constexpr ColorComponentMask ColorComponentAll = ColorComponent::Red | ColorComponent::Green | ColorComponent::Blue | ColorComponent::Alpha;
enum class FramebufferType enum class FramebufferType
{ {
Texture, Texture,

View File

@ -23,6 +23,7 @@ namespace Nz
struct RenderDeviceLimits struct RenderDeviceLimits
{ {
UInt64 minStorageBufferOffsetAlignment;
UInt64 minUniformBufferOffsetAlignment; UInt64 minUniformBufferOffsetAlignment;
UInt64 maxStorageBufferSize; UInt64 maxStorageBufferSize;
UInt64 maxUniformBufferSize; UInt64 maxUniformBufferSize;

View File

@ -19,6 +19,7 @@ namespace Nz
struct RenderStates struct RenderStates
{ {
ColorComponentMask colorWriteMask = ColorComponentAll;
FaceFilling faceFilling = FaceFilling::Fill; FaceFilling faceFilling = FaceFilling::Fill;
FaceSide cullingSide = FaceSide::Back; FaceSide cullingSide = FaceSide::Back;
FrontFace frontFace = FrontFace::CounterClockwise; FrontFace frontFace = FrontFace::CounterClockwise;
@ -47,7 +48,6 @@ namespace Nz
} stencilBack, stencilFront; } stencilBack, stencilFront;
bool blending = false; bool blending = false;
bool colorWrite = true;
bool depthBuffer = false; bool depthBuffer = false;
bool depthClamp = false; bool depthClamp = false;
bool depthWrite = true; bool depthWrite = true;

View File

@ -17,7 +17,6 @@ namespace Nz
#define NazaraRenderStateFloatMember(field, maxDiff) if (!NumberEquals(lhs.field, rhs.field, maxDiff)) return false #define NazaraRenderStateFloatMember(field, maxDiff) if (!NumberEquals(lhs.field, rhs.field, maxDiff)) return false
NazaraRenderStateBoolMember(blending); NazaraRenderStateBoolMember(blending);
NazaraRenderStateBoolMember(colorWrite);
NazaraRenderStateBoolMember(depthBuffer); NazaraRenderStateBoolMember(depthBuffer);
NazaraRenderStateBoolMember(depthClamp); NazaraRenderStateBoolMember(depthClamp);
NazaraRenderStateBoolMember(faceCulling); NazaraRenderStateBoolMember(faceCulling);
@ -27,6 +26,7 @@ namespace Nz
if (lhs.depthBuffer) if (lhs.depthBuffer)
NazaraRenderStateBoolMember(depthWrite); NazaraRenderStateBoolMember(depthWrite);
NazaraRenderStateMember(colorWriteMask);
NazaraRenderStateMember(faceFilling); NazaraRenderStateMember(faceFilling);
if (lhs.blending) //< Remember, at this time we know lhs.blending == rhs.blending if (lhs.blending) //< Remember, at this time we know lhs.blending == rhs.blending
@ -91,10 +91,10 @@ namespace std
#define NazaraRenderStateBoolDep(dependency, member) parameterHash |= ((pipelineInfo.dependency && pipelineInfo.member) ? 1U : 0U) << (parameterIndex++) #define NazaraRenderStateBoolDep(dependency, member) parameterHash |= ((pipelineInfo.dependency && pipelineInfo.member) ? 1U : 0U) << (parameterIndex++)
#define NazaraRenderStateEnum(member) Nz::HashCombine(seed, static_cast<Nz::UInt8>(pipelineInfo.member)) #define NazaraRenderStateEnum(member) Nz::HashCombine(seed, static_cast<Nz::UInt8>(pipelineInfo.member))
#define NazaraRenderStateFloat(member, maxDiff) Nz::HashCombine(seed, std::floor(pipelineInfo.member / maxDiff) * maxDiff) #define NazaraRenderStateFloat(member, maxDiff) Nz::HashCombine(seed, std::floor(pipelineInfo.member / maxDiff) * maxDiff)
#define NazaraRenderStateUInt8(member) Nz::HashCombine(seed, pipelineInfo.member)
#define NazaraRenderStateUInt32(member) Nz::HashCombine(seed, pipelineInfo.member) #define NazaraRenderStateUInt32(member) Nz::HashCombine(seed, pipelineInfo.member)
NazaraRenderStateBool(blending); NazaraRenderStateBool(blending);
NazaraRenderStateBool(colorWrite);
NazaraRenderStateBool(depthBuffer); NazaraRenderStateBool(depthBuffer);
NazaraRenderStateBool(depthClamp); NazaraRenderStateBool(depthClamp);
NazaraRenderStateBool(faceCulling); NazaraRenderStateBool(faceCulling);
@ -103,6 +103,7 @@ namespace std
NazaraRenderStateBoolDep(depthBuffer, depthWrite); NazaraRenderStateBoolDep(depthBuffer, depthWrite);
NazaraRenderStateUInt8(colorWriteMask);
NazaraRenderStateEnum(faceFilling); NazaraRenderStateEnum(faceFilling);
if (pipelineInfo.blending) //< we don't care about blending state if blending isn't enabled if (pipelineInfo.blending) //< we don't care about blending state if blending isn't enabled

View File

@ -62,7 +62,7 @@ namespace Nz
struct Binding struct Binding
{ {
std::size_t bindingIndex; UInt32 bindingIndex;
std::variant<StorageBufferBinding, TextureBinding, UniformBufferBinding> content; std::variant<StorageBufferBinding, TextureBinding, UniformBufferBinding> content;
}; };

View File

@ -16,7 +16,6 @@
namespace Nz namespace Nz
{ {
class AbstractTextDrawer; class AbstractTextDrawer;
class MaterialPass;
class NAZARA_WIDGETS_API ButtonWidget : public BaseWidget class NAZARA_WIDGETS_API ButtonWidget : public BaseWidget
{ {

View File

@ -16,8 +16,6 @@
namespace Nz namespace Nz
{ {
class MaterialPass;
class NAZARA_WIDGETS_API CheckboxWidget : public BaseWidget class NAZARA_WIDGETS_API CheckboxWidget : public BaseWidget
{ {
public: public:

View File

@ -34,20 +34,20 @@ namespace Nz
DefaultWidgetTheme& operator=(DefaultWidgetTheme&&) = default; DefaultWidgetTheme& operator=(DefaultWidgetTheme&&) = default;
private: private:
std::shared_ptr<Material> m_buttonMaterial; std::shared_ptr<MaterialInstance> m_buttonMaterial;
std::shared_ptr<Material> m_buttonHoveredMaterial; std::shared_ptr<MaterialInstance> m_buttonHoveredMaterial;
std::shared_ptr<Material> m_buttonPressedHoveredMaterial; std::shared_ptr<MaterialInstance> m_buttonPressedHoveredMaterial;
std::shared_ptr<Material> m_buttonPressedMaterial; std::shared_ptr<MaterialInstance> m_buttonPressedMaterial;
std::shared_ptr<Material> m_checkboxBackgroundMaterial; std::shared_ptr<MaterialInstance> m_checkboxBackgroundMaterial;
std::shared_ptr<Material> m_checkboxBackgroundHoveredMaterial; std::shared_ptr<MaterialInstance> m_checkboxBackgroundHoveredMaterial;
std::shared_ptr<Material> m_checkboxCheckMaterial; std::shared_ptr<MaterialInstance> m_checkboxCheckMaterial;
std::shared_ptr<Material> m_checkboxTristateMaterial; std::shared_ptr<MaterialInstance> m_checkboxTristateMaterial;
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_scrollbarBackgroundHorizontalMaterial; std::shared_ptr<MaterialInstance> m_scrollbarBackgroundHorizontalMaterial;
std::shared_ptr<Material> m_scrollbarBackgroundVerticalMaterial; std::shared_ptr<MaterialInstance> m_scrollbarBackgroundVerticalMaterial;
std::shared_ptr<Material> m_scrollbarButtonMaterial; std::shared_ptr<MaterialInstance> m_scrollbarButtonMaterial;
std::shared_ptr<Material> m_scrollbarButtonHoveredMaterial; std::shared_ptr<MaterialInstance> m_scrollbarButtonHoveredMaterial;
std::shared_ptr<Material> m_scrollbarButtonGrabbedMaterial; std::shared_ptr<MaterialInstance> m_scrollbarButtonGrabbedMaterial;
}; };
} }

View File

@ -16,14 +16,13 @@
namespace Nz namespace Nz
{ {
class AbstractTextDrawer; class AbstractTextDrawer;
class MaterialPass;
class NAZARA_WIDGETS_API ImageButtonWidget : public BaseWidget class NAZARA_WIDGETS_API ImageButtonWidget : public BaseWidget
{ {
public: public:
inline ImageButtonWidget(BaseWidget* parent, std::shared_ptr<Material> material); inline ImageButtonWidget(BaseWidget* parent, std::shared_ptr<MaterialInstance> material);
inline ImageButtonWidget(BaseWidget* parent, std::shared_ptr<Material> material, float cornerSize, float cornerTexCoords); inline ImageButtonWidget(BaseWidget* parent, std::shared_ptr<MaterialInstance> material, float cornerSize, float cornerTexCoords);
ImageButtonWidget(BaseWidget* parent, std::shared_ptr<Material> material, std::shared_ptr<Material> hoveredMaterial, std::shared_ptr<Material> pressedMaterial, float cornerSize, float cornerTexCoords); ImageButtonWidget(BaseWidget* parent, std::shared_ptr<MaterialInstance> material, std::shared_ptr<MaterialInstance> hoveredMaterial, std::shared_ptr<MaterialInstance> pressedMaterial, float cornerSize, float cornerTexCoords);
ImageButtonWidget(const ImageButtonWidget&) = delete; ImageButtonWidget(const ImageButtonWidget&) = delete;
ImageButtonWidget(ImageButtonWidget&&) = default; ImageButtonWidget(ImageButtonWidget&&) = default;
~ImageButtonWidget() = default; ~ImageButtonWidget() = default;
@ -31,16 +30,16 @@ namespace Nz
inline const Color& GetColor() const; inline const Color& GetColor() const;
inline float GetCornerSize() const; inline float GetCornerSize() const;
inline float GetCornerTexCoords() const; inline float GetCornerTexCoords() const;
inline const std::shared_ptr<Material>& GetHoveredMaterial() const; inline const std::shared_ptr<MaterialInstance>& GetHoveredMaterial() const;
inline const std::shared_ptr<Material>& GetMaterial() const; inline const std::shared_ptr<MaterialInstance>& GetMaterial() const;
inline const std::shared_ptr<Material>& GetPressedMaterial() const; inline const std::shared_ptr<MaterialInstance>& GetPressedMaterial() const;
inline const Rectf& GetTextureCoords() const; inline const Rectf& GetTextureCoords() const;
inline void SetColor(const Color& color); inline void SetColor(const Color& color);
inline void SetCorner(float size, float texcoords); inline void SetCorner(float size, float texcoords);
inline void SetHoveredMaterial(std::shared_ptr<Material> material); inline void SetHoveredMaterial(std::shared_ptr<MaterialInstance> material);
inline void SetMaterial(std::shared_ptr<Material> material); inline void SetMaterial(std::shared_ptr<MaterialInstance> material);
inline void SetPressedMaterial(std::shared_ptr<Material> material); inline void SetPressedMaterial(std::shared_ptr<MaterialInstance> material);
inline void SetTextureCoords(const Rectf& coords); inline void SetTextureCoords(const Rectf& coords);
ImageButtonWidget& operator=(const ImageButtonWidget&) = delete; ImageButtonWidget& operator=(const ImageButtonWidget&) = delete;
@ -61,9 +60,9 @@ namespace Nz
void UpdatePreferredSize(); void UpdatePreferredSize();
std::unique_ptr<ImageButtonWidgetStyle> m_style; std::unique_ptr<ImageButtonWidgetStyle> m_style;
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::shared_ptr<Material> m_pressedMaterial; std::shared_ptr<MaterialInstance> m_pressedMaterial;
Color m_color; Color m_color;
Rectf m_textureCoords; Rectf m_textureCoords;
float m_cornerSize; float m_cornerSize;

View File

@ -7,12 +7,12 @@
namespace Nz namespace Nz
{ {
inline ImageButtonWidget::ImageButtonWidget(BaseWidget* parent, std::shared_ptr<Material> material) : inline ImageButtonWidget::ImageButtonWidget(BaseWidget* parent, std::shared_ptr<MaterialInstance> material) :
ImageButtonWidget(parent, std::move(material), {}, {}, 0.f, 0.f) ImageButtonWidget(parent, std::move(material), {}, {}, 0.f, 0.f)
{ {
} }
inline ImageButtonWidget::ImageButtonWidget(BaseWidget* parent, std::shared_ptr<Material> material, float cornerSize, float cornerTexCoords) : inline ImageButtonWidget::ImageButtonWidget(BaseWidget* parent, std::shared_ptr<MaterialInstance> material, float cornerSize, float cornerTexCoords) :
ImageButtonWidget(parent, std::move(material), {}, {}, cornerSize, cornerTexCoords) ImageButtonWidget(parent, std::move(material), {}, {}, cornerSize, cornerTexCoords)
{ {
} }
@ -32,17 +32,17 @@ namespace Nz
return m_cornerTexCoords; return m_cornerTexCoords;
} }
inline const std::shared_ptr<Material>& ImageButtonWidget::GetHoveredMaterial() const inline const std::shared_ptr<MaterialInstance>& ImageButtonWidget::GetHoveredMaterial() const
{ {
return m_hoveredMaterial; return m_hoveredMaterial;
} }
inline const std::shared_ptr<Material>& ImageButtonWidget::GetMaterial() const inline const std::shared_ptr<MaterialInstance>& ImageButtonWidget::GetMaterial() const
{ {
return m_material; return m_material;
} }
inline const std::shared_ptr<Material>& ImageButtonWidget::GetPressedMaterial() const inline const std::shared_ptr<MaterialInstance>& ImageButtonWidget::GetPressedMaterial() const
{ {
return m_pressedMaterial; return m_pressedMaterial;
} }
@ -67,14 +67,14 @@ namespace Nz
m_style->OnUpdate(); m_style->OnUpdate();
} }
inline void ImageButtonWidget::SetHoveredMaterial(std::shared_ptr<Material> material) inline void ImageButtonWidget::SetHoveredMaterial(std::shared_ptr<MaterialInstance> material)
{ {
m_hoveredMaterial = std::move(material); m_hoveredMaterial = std::move(material);
m_style->OnUpdate(); m_style->OnUpdate();
} }
inline void ImageButtonWidget::SetMaterial(std::shared_ptr<Material> material) inline void ImageButtonWidget::SetMaterial(std::shared_ptr<MaterialInstance> material)
{ {
m_material = std::move(material); m_material = std::move(material);
UpdatePreferredSize(); UpdatePreferredSize();
@ -82,7 +82,7 @@ namespace Nz
m_style->OnUpdate(); m_style->OnUpdate();
} }
inline void ImageButtonWidget::SetPressedMaterial(std::shared_ptr<Material> material) inline void ImageButtonWidget::SetPressedMaterial(std::shared_ptr<MaterialInstance> material)
{ {
m_pressedMaterial = std::move(material); m_pressedMaterial = std::move(material);

View File

@ -17,17 +17,17 @@ namespace Nz
class NAZARA_WIDGETS_API ImageWidget : public BaseWidget class NAZARA_WIDGETS_API ImageWidget : public BaseWidget
{ {
public: public:
ImageWidget(BaseWidget* parent, std::shared_ptr<Material> material); ImageWidget(BaseWidget* parent, std::shared_ptr<MaterialInstance> material);
ImageWidget(const ImageWidget&) = delete; ImageWidget(const ImageWidget&) = delete;
ImageWidget(ImageWidget&&) = default; ImageWidget(ImageWidget&&) = default;
~ImageWidget() = default; ~ImageWidget() = default;
inline const Color& GetColor() const; inline const Color& GetColor() const;
inline const std::shared_ptr<Material>& GetMaterial() const; inline const std::shared_ptr<MaterialInstance>& GetMaterial() const;
inline const Rectf& GetTextureCoords() const; inline const Rectf& GetTextureCoords() const;
inline void SetColor(const Color& color); inline void SetColor(const Color& color);
inline void SetMaterial(const std::shared_ptr<Material>& texture); inline void SetMaterial(const std::shared_ptr<MaterialInstance>& texture);
inline void SetTextureCoords(const Rectf& coords); inline void SetTextureCoords(const Rectf& coords);
inline void SetTextureRect(const Rectf& rect); inline void SetTextureRect(const Rectf& rect);

View File

@ -12,7 +12,7 @@ namespace Nz
return m_sprite->GetColor(); return m_sprite->GetColor();
} }
inline const std::shared_ptr<Material>& ImageWidget::GetMaterial() const inline const std::shared_ptr<MaterialInstance>& ImageWidget::GetMaterial() const
{ {
return m_sprite->GetMaterial(); return m_sprite->GetMaterial();
} }
@ -27,7 +27,7 @@ namespace Nz
m_sprite->SetColor(color); m_sprite->SetColor(color);
} }
inline void ImageWidget::SetMaterial(const std::shared_ptr<Material>& texture) inline void ImageWidget::SetMaterial(const std::shared_ptr<MaterialInstance>& texture)
{ {
m_sprite->SetMaterial(texture); m_sprite->SetMaterial(texture);
UpdatePreferredSize(); UpdatePreferredSize();

View File

@ -16,7 +16,6 @@
namespace Nz namespace Nz
{ {
class AbstractTextDrawer; class AbstractTextDrawer;
class MaterialPass;
class NAZARA_WIDGETS_API ScrollbarButtonWidget : public BaseWidget class NAZARA_WIDGETS_API ScrollbarButtonWidget : public BaseWidget
{ {

View File

@ -40,10 +40,10 @@ namespace Nz
struct StyleConfig struct StyleConfig
{ {
std::shared_ptr<Material> hoveredMaterial; std::shared_ptr<MaterialInstance> hoveredMaterial;
std::shared_ptr<Material> material; std::shared_ptr<MaterialInstance> material;
std::shared_ptr<Material> pressedMaterial; std::shared_ptr<MaterialInstance> pressedMaterial;
std::shared_ptr<Material> pressedHoveredMaterial; std::shared_ptr<MaterialInstance> pressedHoveredMaterial;
float cornerSize; float cornerSize;
float cornerTexCoords; float cornerTexCoords;
}; };
@ -52,10 +52,10 @@ namespace Nz
virtual void UpdateMaterial(bool hovered, bool pressed); virtual void UpdateMaterial(bool hovered, bool pressed);
private: private:
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::shared_ptr<Material> m_pressedMaterial; std::shared_ptr<MaterialInstance> m_pressedMaterial;
std::shared_ptr<Material> m_pressedHoveredMaterial; std::shared_ptr<MaterialInstance> m_pressedHoveredMaterial;
std::shared_ptr<SlicedSprite> m_sprite; std::shared_ptr<SlicedSprite> m_sprite;
std::shared_ptr<TextSprite> m_textSprite; std::shared_ptr<TextSprite> m_textSprite;
entt::entity m_spriteEntity; entt::entity m_spriteEntity;
@ -87,10 +87,10 @@ namespace Nz
struct StyleConfig struct StyleConfig
{ {
std::shared_ptr<Material> backgroundMaterial; std::shared_ptr<MaterialInstance> backgroundMaterial;
std::shared_ptr<Material> backgroundHoveredMaterial; std::shared_ptr<MaterialInstance> backgroundHoveredMaterial;
std::shared_ptr<Material> checkMaterial; std::shared_ptr<MaterialInstance> checkMaterial;
std::shared_ptr<Material> tristateMaterial; std::shared_ptr<MaterialInstance> tristateMaterial;
float backgroundCornerSize; float backgroundCornerSize;
float backgroundCornerTexCoords; float backgroundCornerTexCoords;
}; };
@ -99,10 +99,10 @@ namespace Nz
virtual void UpdateMaterial(bool hovered); virtual void UpdateMaterial(bool hovered);
private: private:
std::shared_ptr<Material> m_checkMaterial; std::shared_ptr<MaterialInstance> m_checkMaterial;
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::shared_ptr<Material> m_tristateMaterial; std::shared_ptr<MaterialInstance> m_tristateMaterial;
std::shared_ptr<Sprite> m_checkSprite; std::shared_ptr<Sprite> m_checkSprite;
std::shared_ptr<SlicedSprite> m_backgroundSprite; std::shared_ptr<SlicedSprite> m_backgroundSprite;
entt::entity m_backgroundEntity; entt::entity m_backgroundEntity;
@ -135,7 +135,7 @@ namespace Nz
struct StyleConfig struct StyleConfig
{ {
std::shared_ptr<Material> hoveredMaterial; std::shared_ptr<MaterialInstance> hoveredMaterial;
float hoveredCornerSize; float hoveredCornerSize;
float hoveredCornerTexCoords; float hoveredCornerTexCoords;
}; };
@ -154,7 +154,7 @@ namespace Nz
class NAZARA_WIDGETS_API SimpleLabelWidgetStyle : public LabelWidgetStyle class NAZARA_WIDGETS_API SimpleLabelWidgetStyle : public LabelWidgetStyle
{ {
public: public:
SimpleLabelWidgetStyle(LabelWidget* labelWidget, std::shared_ptr<Material> material, std::shared_ptr<Material> hoveredMaterial = {}); SimpleLabelWidgetStyle(LabelWidget* labelWidget, std::shared_ptr<MaterialInstance> material, std::shared_ptr<MaterialInstance> hoveredMaterial = {});
SimpleLabelWidgetStyle(const SimpleLabelWidgetStyle&) = delete; SimpleLabelWidgetStyle(const SimpleLabelWidgetStyle&) = delete;
SimpleLabelWidgetStyle(SimpleLabelWidgetStyle&&) = default; SimpleLabelWidgetStyle(SimpleLabelWidgetStyle&&) = default;
~SimpleLabelWidgetStyle() = default; ~SimpleLabelWidgetStyle() = default;
@ -174,8 +174,8 @@ namespace Nz
virtual void UpdateMaterial(bool hovered); virtual void UpdateMaterial(bool hovered);
private: private:
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::shared_ptr<TextSprite> m_textSprite; std::shared_ptr<TextSprite> m_textSprite;
entt::entity m_entity; entt::entity m_entity;
}; };
@ -196,8 +196,8 @@ namespace Nz
SimpleScrollAreaWidgetStyle& operator=(SimpleScrollAreaWidgetStyle&&) = default; SimpleScrollAreaWidgetStyle& operator=(SimpleScrollAreaWidgetStyle&&) = default;
private: private:
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::shared_ptr<TextSprite> m_textSprite; std::shared_ptr<TextSprite> m_textSprite;
entt::entity m_entity; entt::entity m_entity;
}; };
@ -221,8 +221,8 @@ namespace Nz
struct StyleConfig struct StyleConfig
{ {
std::shared_ptr<Material> backgroundHorizontalMaterial; std::shared_ptr<MaterialInstance> backgroundHorizontalMaterial;
std::shared_ptr<Material> backgroundVerticalMaterial; std::shared_ptr<MaterialInstance> backgroundVerticalMaterial;
}; };
private: private:
@ -257,10 +257,10 @@ namespace Nz
struct StyleConfig struct StyleConfig
{ {
std::shared_ptr<Material> material; std::shared_ptr<MaterialInstance> material;
std::shared_ptr<Material> grabbedMaterial; std::shared_ptr<MaterialInstance> grabbedMaterial;
std::shared_ptr<Material> grabbedHoveredMaterial; std::shared_ptr<MaterialInstance> grabbedHoveredMaterial;
std::shared_ptr<Material> hoveredMaterial; std::shared_ptr<MaterialInstance> hoveredMaterial;
float cornerSize; float cornerSize;
float cornerTexCoords; float cornerTexCoords;
}; };
@ -270,10 +270,10 @@ namespace Nz
private: private:
StyleConfig m_config; StyleConfig m_config;
std::shared_ptr<Material> m_hoveredMaterial; std::shared_ptr<MaterialInstance> m_hoveredMaterial;
std::shared_ptr<Material> m_material; std::shared_ptr<MaterialInstance> m_material;
std::shared_ptr<Material> m_pressedMaterial; std::shared_ptr<MaterialInstance> m_pressedMaterial;
std::shared_ptr<Material> m_pressedHoveredMaterial; std::shared_ptr<MaterialInstance> m_pressedHoveredMaterial;
std::shared_ptr<SlicedSprite> m_sprite; std::shared_ptr<SlicedSprite> m_sprite;
entt::entity m_entity; entt::entity m_entity;
bool m_isHovered; bool m_isHovered;

View File

@ -56,18 +56,18 @@ namespace Nz
struct Config struct Config
{ {
std::shared_ptr<Material> scrollbarButtonDownMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonDownMaterial;
std::shared_ptr<Material> scrollbarButtonDownHoveredMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonDownHoveredMaterial;
std::shared_ptr<Material> scrollbarButtonDownPressedMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonDownPressedMaterial;
std::shared_ptr<Material> scrollbarButtonLeftMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonLeftMaterial;
std::shared_ptr<Material> scrollbarButtonLeftHoveredMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonLeftHoveredMaterial;
std::shared_ptr<Material> scrollbarButtonLeftPressedMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonLeftPressedMaterial;
std::shared_ptr<Material> scrollbarButtonRightMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonRightMaterial;
std::shared_ptr<Material> scrollbarButtonRightHoveredMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonRightHoveredMaterial;
std::shared_ptr<Material> scrollbarButtonRightPressedMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonRightPressedMaterial;
std::shared_ptr<Material> scrollbarButtonUpMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonUpMaterial;
std::shared_ptr<Material> scrollbarButtonUpHoveredMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonUpHoveredMaterial;
std::shared_ptr<Material> scrollbarButtonUpPressedMaterial; std::shared_ptr<MaterialInstance> scrollbarButtonUpPressedMaterial;
float scrollbarButtonCornerSize; float scrollbarButtonCornerSize;
float scrollbarButtonCornerTexcoords; float scrollbarButtonCornerTexcoords;
}; };

Some files were not shown because too many files have changed in this diff Show More