mirror of
https://github.com/overte-org/overte.git
synced 2025-08-06 10:14:28 +02:00
more clean up
This commit is contained in:
parent
cde17ecaab
commit
51594fefa2
20 changed files with 119 additions and 74 deletions
|
@ -12,6 +12,8 @@
|
||||||
<@def DEFERRED_BUFFER_WRITE_SLH@>
|
<@def DEFERRED_BUFFER_WRITE_SLH@>
|
||||||
|
|
||||||
<@include DeferredBuffer.slh@>
|
<@include DeferredBuffer.slh@>
|
||||||
|
<@include LightingModel.slh@>
|
||||||
|
|
||||||
|
|
||||||
layout(location = 0) out vec4 _fragColor0;
|
layout(location = 0) out vec4 _fragColor0;
|
||||||
layout(location = 1) out vec4 _fragColor1;
|
layout(location = 1) out vec4 _fragColor1;
|
||||||
|
@ -38,6 +40,7 @@ void packDeferredFragment(vec3 normal, float alpha, vec3 albedo, float roughness
|
||||||
if (alpha != 1.0) {
|
if (alpha != 1.0) {
|
||||||
discard;
|
discard;
|
||||||
}
|
}
|
||||||
|
emissive *= isEmissiveEnabled();
|
||||||
_fragColor0 = vec4(albedo, ((scattering > 0.0) ? packScatteringMetallic(metallic) : packShadedMetallic(metallic)));
|
_fragColor0 = vec4(albedo, ((scattering > 0.0) ? packScatteringMetallic(metallic) : packShadedMetallic(metallic)));
|
||||||
_fragColor1 = vec4(packNormal(normal), clamp(roughness, 0.0, 1.0));
|
_fragColor1 = vec4(packNormal(normal), clamp(roughness, 0.0, 1.0));
|
||||||
_fragColor2 = vec4(((scattering > 0.0) ? vec3(scattering) : emissive), occlusion);
|
_fragColor2 = vec4(((scattering > 0.0) ? vec3(scattering) : emissive), occlusion);
|
||||||
|
@ -50,10 +53,15 @@ void packDeferredFragmentLightmap(vec3 normal, float alpha, vec3 albedo, float r
|
||||||
if (alpha != 1.0) {
|
if (alpha != 1.0) {
|
||||||
discard;
|
discard;
|
||||||
}
|
}
|
||||||
|
|
||||||
_fragColor0 = vec4(albedo, packLightmappedMetallic(metallic));
|
_fragColor0 = vec4(albedo, packLightmappedMetallic(metallic));
|
||||||
_fragColor1 = vec4(packNormal(normal), clamp(roughness, 0.0, 1.0));
|
_fragColor1 = vec4(packNormal(normal), clamp(roughness, 0.0, 1.0));
|
||||||
_fragColor2 = vec4(lightmap, 1.0);
|
_fragColor2 = vec4(lightmap, 1.0);
|
||||||
_fragColor3 = vec4(albedo * lightmap, 1.0);
|
|
||||||
|
_fragColor3 = vec4(lightmap * isLightmapEnabled(), 1.0);
|
||||||
|
if (isAlbedoEnabled() > 0.0) {
|
||||||
|
_fragColor3.rgb *= albedo;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void packDeferredFragmentUnlit(vec3 normal, float alpha, vec3 color) {
|
void packDeferredFragmentUnlit(vec3 normal, float alpha, vec3 color) {
|
||||||
|
@ -63,7 +71,7 @@ void packDeferredFragmentUnlit(vec3 normal, float alpha, vec3 color) {
|
||||||
_fragColor0 = vec4(color, packUnlit());
|
_fragColor0 = vec4(color, packUnlit());
|
||||||
_fragColor1 = vec4(packNormal(normal), 1.0);
|
_fragColor1 = vec4(packNormal(normal), 1.0);
|
||||||
_fragColor2 = vec4(vec3(0.0), 1.0);
|
_fragColor2 = vec4(vec3(0.0), 1.0);
|
||||||
_fragColor3 = vec4(color, 1.0);
|
_fragColor3 = vec4(color * isUnlitEnabled(), 1.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void packDeferredFragmentTranslucent(vec3 normal, float alpha, vec3 albedo, vec3 fresnel, float roughness) {
|
void packDeferredFragmentTranslucent(vec3 normal, float alpha, vec3 albedo, vec3 fresnel, float roughness) {
|
||||||
|
|
|
@ -14,7 +14,6 @@
|
||||||
<@include model/Light.slh@>
|
<@include model/Light.slh@>
|
||||||
|
|
||||||
<@include LightingModel.slh@>
|
<@include LightingModel.slh@>
|
||||||
<$declareLightingModel()$>
|
|
||||||
|
|
||||||
<@include LightAmbient.slh@>
|
<@include LightAmbient.slh@>
|
||||||
<@include LightDirectional.slh@>
|
<@include LightDirectional.slh@>
|
||||||
|
|
|
@ -66,9 +66,9 @@ enum DeferredShader_MapSlot {
|
||||||
};
|
};
|
||||||
enum DeferredShader_BufferSlot {
|
enum DeferredShader_BufferSlot {
|
||||||
DEFERRED_FRAME_TRANSFORM_BUFFER_SLOT = 0,
|
DEFERRED_FRAME_TRANSFORM_BUFFER_SLOT = 0,
|
||||||
LIGHTING_MODEL_BUFFER_SLOT,
|
|
||||||
SCATTERING_PARAMETERS_BUFFER_SLOT,
|
SCATTERING_PARAMETERS_BUFFER_SLOT,
|
||||||
LIGHT_GPU_SLOT,
|
LIGHTING_MODEL_BUFFER_SLOT = render::ShapePipeline::Slot::LIGHTING_MODEL,
|
||||||
|
LIGHT_GPU_SLOT = render::ShapePipeline::Slot::LIGHT,
|
||||||
};
|
};
|
||||||
|
|
||||||
static void loadLightProgram(const char* vertSource, const char* fragSource, bool lightVolume, gpu::PipelinePointer& program, LightLocationsPtr& locations);
|
static void loadLightProgram(const char* vertSource, const char* fragSource, bool lightVolume, gpu::PipelinePointer& program, LightLocationsPtr& locations);
|
||||||
|
@ -355,16 +355,19 @@ void PreparePrimaryFramebuffer::run(const SceneContextPointer& sceneContext, con
|
||||||
primaryFramebuffer = _primaryFramebuffer;
|
primaryFramebuffer = _primaryFramebuffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
void PrepareDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const gpu::FramebufferPointer& primaryFramebuffer, Outputs& output) {
|
void PrepareDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& inputs, Outputs& outputs) {
|
||||||
auto args = renderContext->args;
|
auto args = renderContext->args;
|
||||||
|
|
||||||
|
auto primaryFramebuffer = inputs.get0();
|
||||||
|
auto lightingModel = inputs.get1();
|
||||||
|
|
||||||
if (!_deferredFramebuffer) {
|
if (!_deferredFramebuffer) {
|
||||||
_deferredFramebuffer = std::make_shared<DeferredFramebuffer>();
|
_deferredFramebuffer = std::make_shared<DeferredFramebuffer>();
|
||||||
}
|
}
|
||||||
_deferredFramebuffer->updatePrimaryDepth(primaryFramebuffer->getDepthStencilBuffer());
|
_deferredFramebuffer->updatePrimaryDepth(primaryFramebuffer->getDepthStencilBuffer());
|
||||||
|
|
||||||
output.edit0() = _deferredFramebuffer;
|
outputs.edit0() = _deferredFramebuffer;
|
||||||
output.edit1() = _deferredFramebuffer->getLightingFramebuffer();
|
outputs.edit1() = _deferredFramebuffer->getLightingFramebuffer();
|
||||||
|
|
||||||
|
|
||||||
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
||||||
|
@ -372,14 +375,7 @@ void PrepareDeferred::run(const SceneContextPointer& sceneContext, const RenderC
|
||||||
batch.setViewportTransform(args->_viewport);
|
batch.setViewportTransform(args->_viewport);
|
||||||
batch.setStateScissorRect(args->_viewport);
|
batch.setStateScissorRect(args->_viewport);
|
||||||
|
|
||||||
// Clear Lighting buffer
|
|
||||||
/* auto lightingFbo = DependencyManager::get<FramebufferCache>()->getLightingFramebuffer();
|
|
||||||
|
|
||||||
batch.setFramebuffer(lightingFbo);
|
|
||||||
batch.clearColorFramebuffer(gpu::Framebuffer::BUFFER_COLOR0, vec4(vec3(0), 0), true);
|
|
||||||
*/
|
|
||||||
// Clear deferred
|
// Clear deferred
|
||||||
// auto deferredFbo = DependencyManager::get<FramebufferCache>()->getDeferredFramebuffer();
|
|
||||||
auto deferredFbo = _deferredFramebuffer->getDeferredFramebuffer();
|
auto deferredFbo = _deferredFramebuffer->getDeferredFramebuffer();
|
||||||
batch.setFramebuffer(deferredFbo);
|
batch.setFramebuffer(deferredFbo);
|
||||||
|
|
||||||
|
@ -389,6 +385,9 @@ void PrepareDeferred::run(const SceneContextPointer& sceneContext, const RenderC
|
||||||
gpu::Framebuffer::BUFFER_DEPTH |
|
gpu::Framebuffer::BUFFER_DEPTH |
|
||||||
gpu::Framebuffer::BUFFER_STENCIL,
|
gpu::Framebuffer::BUFFER_STENCIL,
|
||||||
vec4(vec3(0), 0), 1.0, 0.0, true);
|
vec4(vec3(0), 0), 1.0, 0.0, true);
|
||||||
|
|
||||||
|
// For the rest of the rendering, bind the lighting model
|
||||||
|
batch.setUniformBuffer(LIGHTING_MODEL_BUFFER_SLOT, lightingModel->getParametersBuffer());
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -646,7 +645,7 @@ void RenderDeferredCleanup::run(const render::SceneContextPointer& sceneContext,
|
||||||
batch.setResourceTexture(SCATTERING_SPECULAR_UNIT, nullptr);
|
batch.setResourceTexture(SCATTERING_SPECULAR_UNIT, nullptr);
|
||||||
|
|
||||||
batch.setUniformBuffer(SCATTERING_PARAMETERS_BUFFER_SLOT, nullptr);
|
batch.setUniformBuffer(SCATTERING_PARAMETERS_BUFFER_SLOT, nullptr);
|
||||||
batch.setUniformBuffer(LIGHTING_MODEL_BUFFER_SLOT, nullptr);
|
// batch.setUniformBuffer(LIGHTING_MODEL_BUFFER_SLOT, nullptr);
|
||||||
batch.setUniformBuffer(DEFERRED_FRAME_TRANSFORM_BUFFER_SLOT, nullptr);
|
batch.setUniformBuffer(DEFERRED_FRAME_TRANSFORM_BUFFER_SLOT, nullptr);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -117,12 +117,14 @@ public:
|
||||||
|
|
||||||
class PrepareDeferred {
|
class PrepareDeferred {
|
||||||
public:
|
public:
|
||||||
|
// Inputs: primaryFramebuffer and lightingModel
|
||||||
|
using Inputs = render::VaryingSet2 <gpu::FramebufferPointer, LightingModelPointer>;
|
||||||
// Output: DeferredFramebuffer, LightingFramebuffer
|
// Output: DeferredFramebuffer, LightingFramebuffer
|
||||||
using Outputs = render::VaryingSet2<DeferredFramebufferPointer, gpu::FramebufferPointer>;
|
using Outputs = render::VaryingSet2<DeferredFramebufferPointer, gpu::FramebufferPointer>;
|
||||||
|
|
||||||
using JobModel = render::Job::ModelIO<PrepareDeferred, gpu::FramebufferPointer, Outputs>;
|
using JobModel = render::Job::ModelIO<PrepareDeferred, Inputs, Outputs>;
|
||||||
|
|
||||||
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const gpu::FramebufferPointer& primaryFramebuffer, Outputs& output);
|
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs, Outputs& outputs);
|
||||||
|
|
||||||
DeferredFramebufferPointer _deferredFramebuffer;
|
DeferredFramebufferPointer _deferredFramebuffer;
|
||||||
};
|
};
|
||||||
|
|
|
@ -37,7 +37,7 @@ void evalLightingPoint(out vec3 diffuse, out vec3 specular, Light light,
|
||||||
diffuse *= lightEnergy * isDiffuseEnabled() * isPointEnabled();
|
diffuse *= lightEnergy * isDiffuseEnabled() * isPointEnabled();
|
||||||
specular *= lightEnergy * isSpecularEnabled() * isPointEnabled();
|
specular *= lightEnergy * isSpecularEnabled() * isPointEnabled();
|
||||||
|
|
||||||
if (getLightShowContour(light) > 0.0) {
|
if (isShowLightContour() > 0.0) {
|
||||||
// Show edge
|
// Show edge
|
||||||
float edge = abs(2.0 * ((getLightRadius(light) - fragLightDistance) / (0.1)) - 1.0);
|
float edge = abs(2.0 * ((getLightRadius(light) - fragLightDistance) / (0.1)) - 1.0);
|
||||||
if (edge < 1) {
|
if (edge < 1) {
|
||||||
|
|
|
@ -38,7 +38,7 @@ void evalLightingSpot(out vec3 diffuse, out vec3 specular, Light light,
|
||||||
diffuse *= lightEnergy * isDiffuseEnabled() * isSpotEnabled();
|
diffuse *= lightEnergy * isDiffuseEnabled() * isSpotEnabled();
|
||||||
specular *= lightEnergy * isSpecularEnabled() * isSpotEnabled();
|
specular *= lightEnergy * isSpecularEnabled() * isSpotEnabled();
|
||||||
|
|
||||||
if (getLightShowContour(light) > 0.0) {
|
if (isShowLightContour() > 0.0) {
|
||||||
// Show edges
|
// Show edges
|
||||||
float edgeDistR = (getLightRadius(light) - fragLightDistance);
|
float edgeDistR = (getLightRadius(light) - fragLightDistance);
|
||||||
float edgeDistS = dot(fragLightDistance * vec2(cosSpotAngle, sqrt(1.0 - cosSpotAngle * cosSpotAngle)), -getLightSpotOutsideNormal2(light));
|
float edgeDistS = dot(fragLightDistance * vec2(cosSpotAngle, sqrt(1.0 - cosSpotAngle * cosSpotAngle)), -getLightSpotOutsideNormal2(light));
|
||||||
|
|
|
@ -122,7 +122,7 @@ void LightingModel::setShowLightContour(bool enable) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
bool LightingModel::isShowLightContourEnabled() const {
|
bool LightingModel::isShowLightContourEnabled() const {
|
||||||
return (bool)_parametersBuffer.get<Parameters>().showLightContour;
|
return (bool)(_parametersBuffer.get<Parameters>().showLightContour > 0.0);
|
||||||
}
|
}
|
||||||
|
|
||||||
MakeLightingModel::MakeLightingModel() {
|
MakeLightingModel::MakeLightingModel() {
|
||||||
|
|
|
@ -81,7 +81,7 @@ protected:
|
||||||
float enablePointLight{ 1.0f };
|
float enablePointLight{ 1.0f };
|
||||||
float enableSpotLight{ 1.0f };
|
float enableSpotLight{ 1.0f };
|
||||||
|
|
||||||
float showLightContour{ 1.0f };
|
float showLightContour{ 0.0f }; // false by default
|
||||||
glm::vec3 spares{ 0.0f };
|
glm::vec3 spares{ 0.0f };
|
||||||
|
|
||||||
Parameters() {}
|
Parameters() {}
|
||||||
|
@ -132,7 +132,7 @@ public:
|
||||||
bool enablePointLight{ true };
|
bool enablePointLight{ true };
|
||||||
bool enableSpotLight{ true };
|
bool enableSpotLight{ true };
|
||||||
|
|
||||||
bool showLightContour{ true };
|
bool showLightContour{ false }; // false by default
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void dirty();
|
void dirty();
|
||||||
|
|
|
@ -12,9 +12,6 @@
|
||||||
<@def LIGHTING_MODEL_SLH@>
|
<@def LIGHTING_MODEL_SLH@>
|
||||||
|
|
||||||
<@func declareLightingModel()@>
|
<@func declareLightingModel()@>
|
||||||
<@endfunc@>
|
|
||||||
|
|
||||||
<@func declareLightingModelMaster()@>
|
|
||||||
|
|
||||||
struct LightingModel {
|
struct LightingModel {
|
||||||
vec4 _UnlitShadedEmissiveLightmap;
|
vec4 _UnlitShadedEmissiveLightmap;
|
||||||
|
@ -66,12 +63,12 @@ float isSpotEnabled() {
|
||||||
return lightingModel._AmbientDirectionalPointSpot.w;
|
return lightingModel._AmbientDirectionalPointSpot.w;
|
||||||
}
|
}
|
||||||
|
|
||||||
float isShowContour() {
|
float isShowLightContour() {
|
||||||
return lightingModel._ShowContour.x;
|
return lightingModel._ShowContour.x;
|
||||||
}
|
}
|
||||||
|
|
||||||
<@endfunc@>
|
<@endfunc@>
|
||||||
<$declareLightingModelMaster()$>
|
<$declareLightingModel()$>
|
||||||
|
|
||||||
<@func declareBeckmannSpecular()@>
|
<@func declareBeckmannSpecular()@>
|
||||||
|
|
||||||
|
|
|
@ -97,28 +97,29 @@ RenderDeferredTask::RenderDeferredTask(CullFunctor cullFunctor) {
|
||||||
// GPU jobs: Start preparing the primary, deferred and lighting buffer
|
// GPU jobs: Start preparing the primary, deferred and lighting buffer
|
||||||
const auto primaryFramebuffer = addJob<PreparePrimaryFramebuffer>("PreparePrimaryBuffer");
|
const auto primaryFramebuffer = addJob<PreparePrimaryFramebuffer>("PreparePrimaryBuffer");
|
||||||
|
|
||||||
const auto deferredAndLightingFramebuffer = addJob<PrepareDeferred>("PrepareDeferred", primaryFramebuffer);
|
const auto prepareDeferredInputs = SurfaceGeometryPass::Inputs(primaryFramebuffer, lightingModel).hasVarying();
|
||||||
const auto deferredFramebuffer = deferredAndLightingFramebuffer.getN<PrepareDeferred::Outputs>(0);
|
const auto prepareDeferredOutputs = addJob<PrepareDeferred>("PrepareDeferred", prepareDeferredInputs);
|
||||||
const auto lightingFramebuffer = deferredAndLightingFramebuffer.getN<PrepareDeferred::Outputs>(1);
|
const auto deferredFramebuffer = prepareDeferredOutputs.getN<PrepareDeferred::Outputs>(0);
|
||||||
|
const auto lightingFramebuffer = prepareDeferredOutputs.getN<PrepareDeferred::Outputs>(1);
|
||||||
|
|
||||||
// Render opaque objects in DeferredBuffer
|
// Render opaque objects in DeferredBuffer
|
||||||
addJob<DrawStateSortDeferred>("DrawOpaqueDeferred", opaques, shapePlumber);
|
const auto opaqueInputs = DrawStateSortDeferred::Inputs(opaques, lightingModel).hasVarying();
|
||||||
|
addJob<DrawStateSortDeferred>("DrawOpaqueDeferred", opaqueInputs, shapePlumber);
|
||||||
|
|
||||||
// Once opaque is all rendered create stencil background
|
// Once opaque is all rendered create stencil background
|
||||||
addJob<DrawStencilDeferred>("DrawOpaqueStencil", deferredFramebuffer);
|
addJob<DrawStencilDeferred>("DrawOpaqueStencil", deferredFramebuffer);
|
||||||
|
|
||||||
|
|
||||||
// Opaque all rendered, generate surface geometry buffers
|
// Opaque all rendered, generate surface geometry buffers
|
||||||
const auto surfaceGeometryPassInputs = render::Varying(SurfaceGeometryPass::Inputs(deferredFrameTransform, deferredFramebuffer));
|
const auto surfaceGeometryPassInputs = SurfaceGeometryPass::Inputs(deferredFrameTransform, deferredFramebuffer).hasVarying();
|
||||||
const auto geometryFramebufferAndCurvatureFramebufferAndDepth = addJob<SurfaceGeometryPass>("SurfaceGeometry", surfaceGeometryPassInputs);
|
const auto surfaceGeometryPassOutputs = addJob<SurfaceGeometryPass>("SurfaceGeometry", surfaceGeometryPassInputs);
|
||||||
const auto surfaceGeometryFramebuffer = geometryFramebufferAndCurvatureFramebufferAndDepth.getN<SurfaceGeometryPass::Outputs>(0);
|
const auto surfaceGeometryFramebuffer = surfaceGeometryPassOutputs.getN<SurfaceGeometryPass::Outputs>(0);
|
||||||
const auto curvatureFramebuffer = geometryFramebufferAndCurvatureFramebufferAndDepth.getN<SurfaceGeometryPass::Outputs>(1);
|
const auto curvatureFramebuffer = surfaceGeometryPassOutputs.getN<SurfaceGeometryPass::Outputs>(1);
|
||||||
const auto linearDepthTexture = geometryFramebufferAndCurvatureFramebufferAndDepth.getN<SurfaceGeometryPass::Outputs>(2);
|
const auto linearDepthTexture = surfaceGeometryPassOutputs.getN<SurfaceGeometryPass::Outputs>(2);
|
||||||
|
|
||||||
const auto curvatureFramebufferAndDepth = render::Varying(BlurGaussianDepthAware::Inputs(curvatureFramebuffer, linearDepthTexture));
|
const auto diffuseCurvaturePassInputs = BlurGaussianDepthAware::Inputs(curvatureFramebuffer, linearDepthTexture).hasVarying();
|
||||||
|
const auto midCurvatureNormalFramebuffer = addJob<render::BlurGaussianDepthAware>("DiffuseCurvatureMid", diffuseCurvaturePassInputs);
|
||||||
const auto midCurvatureNormalFramebuffer = addJob<render::BlurGaussianDepthAware>("DiffuseCurvatureMid", curvatureFramebufferAndDepth);
|
const auto lowCurvatureNormalFramebuffer = addJob<render::BlurGaussianDepthAware>("DiffuseCurvatureLow", diffuseCurvaturePassInputs, true); // THis blur pass generates it s render resource
|
||||||
const auto lowCurvatureNormalFramebuffer = addJob<render::BlurGaussianDepthAware>("DiffuseCurvatureLow", curvatureFramebufferAndDepth, true);
|
|
||||||
|
|
||||||
const auto scatteringResource = addJob<SubsurfaceScattering>("Scattering");
|
const auto scatteringResource = addJob<SubsurfaceScattering>("Scattering");
|
||||||
|
|
||||||
|
@ -128,25 +129,29 @@ RenderDeferredTask::RenderDeferredTask(CullFunctor cullFunctor) {
|
||||||
// Draw Lights just add the lights to the current list of lights to deal with. NOt really gpu job for now.
|
// Draw Lights just add the lights to the current list of lights to deal with. NOt really gpu job for now.
|
||||||
addJob<DrawLight>("DrawLight", lights);
|
addJob<DrawLight>("DrawLight", lights);
|
||||||
|
|
||||||
const auto deferredLightingInputs = render::Varying(RenderDeferred::Inputs(deferredFrameTransform, deferredFramebuffer, lightingModel,
|
const auto deferredLightingInputs = RenderDeferred::Inputs(deferredFrameTransform, deferredFramebuffer, lightingModel,
|
||||||
surfaceGeometryFramebuffer, lowCurvatureNormalFramebuffer, scatteringResource));
|
surfaceGeometryFramebuffer, lowCurvatureNormalFramebuffer, scatteringResource).hasVarying();
|
||||||
|
|
||||||
// DeferredBuffer is complete, now let's shade it into the LightingBuffer
|
// DeferredBuffer is complete, now let's shade it into the LightingBuffer
|
||||||
addJob<RenderDeferred>("RenderDeferred", deferredLightingInputs);
|
addJob<RenderDeferred>("RenderDeferred", deferredLightingInputs);
|
||||||
|
|
||||||
// Use Stencil and draw background in Lighting buffer to complete filling in the opaque
|
// Use Stencil and draw background in Lighting buffer to complete filling in the opaque
|
||||||
addJob<DrawBackgroundDeferred>("DrawBackgroundDeferred", background);
|
const auto backgroundInputs = DrawBackgroundDeferred::Inputs(background, lightingModel).hasVarying();
|
||||||
|
addJob<DrawBackgroundDeferred>("DrawBackgroundDeferred", backgroundInputs);
|
||||||
|
|
||||||
// Render transparent objects forward in LightingBuffer
|
// Render transparent objects forward in LightingBuffer
|
||||||
addJob<DrawDeferred>("DrawTransparentDeferred", transparents, shapePlumber);
|
const auto transparentsInputs = DrawDeferred::Inputs(transparents, lightingModel).hasVarying();
|
||||||
|
addJob<DrawDeferred>("DrawTransparentDeferred", transparentsInputs, shapePlumber);
|
||||||
|
|
||||||
// Lighting Buffer ready for tone mapping
|
// Lighting Buffer ready for tone mapping
|
||||||
const auto toneMappingInputs = render::Varying(ToneMappingDeferred::Inputs(lightingFramebuffer, primaryFramebuffer));
|
const auto toneMappingInputs = render::Varying(ToneMappingDeferred::Inputs(lightingFramebuffer, primaryFramebuffer));
|
||||||
addJob<ToneMappingDeferred>("ToneMapping", toneMappingInputs);
|
addJob<ToneMappingDeferred>("ToneMapping", toneMappingInputs);
|
||||||
|
|
||||||
// Overlays
|
// Overlays
|
||||||
addJob<DrawOverlay3D>("DrawOverlay3DOpaque", overlayOpaques, true);
|
const auto overlayOpaquesInputs = DrawOverlay3D::Inputs(overlayOpaques, lightingModel).hasVarying();
|
||||||
addJob<DrawOverlay3D>("DrawOverlay3DTransparent", overlayTransparents, false);
|
const auto overlayTransparentsInputs = DrawOverlay3D::Inputs(overlayTransparents, lightingModel).hasVarying();
|
||||||
|
addJob<DrawOverlay3D>("DrawOverlay3DOpaque", overlayOpaquesInputs, true);
|
||||||
|
addJob<DrawOverlay3D>("DrawOverlay3DTransparent", overlayTransparentsInputs, false);
|
||||||
|
|
||||||
|
|
||||||
// Debugging stages
|
// Debugging stages
|
||||||
|
@ -198,12 +203,15 @@ void RenderDeferredTask::run(const SceneContextPointer& sceneContext, const Rend
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void DrawDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems) {
|
void DrawDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& inputs) {
|
||||||
assert(renderContext->args);
|
assert(renderContext->args);
|
||||||
assert(renderContext->args->hasViewFrustum());
|
assert(renderContext->args->hasViewFrustum());
|
||||||
|
|
||||||
auto config = std::static_pointer_cast<Config>(renderContext->jobConfig);
|
auto config = std::static_pointer_cast<Config>(renderContext->jobConfig);
|
||||||
|
|
||||||
|
const auto& inItems = inputs.get0();
|
||||||
|
const auto& lightingModel = inputs.get1();
|
||||||
|
|
||||||
RenderArgs* args = renderContext->args;
|
RenderArgs* args = renderContext->args;
|
||||||
|
|
||||||
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
||||||
|
@ -226,12 +234,15 @@ void DrawDeferred::run(const SceneContextPointer& sceneContext, const RenderCont
|
||||||
config->setNumDrawn((int)inItems.size());
|
config->setNumDrawn((int)inItems.size());
|
||||||
}
|
}
|
||||||
|
|
||||||
void DrawStateSortDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems) {
|
void DrawStateSortDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& inputs) {
|
||||||
assert(renderContext->args);
|
assert(renderContext->args);
|
||||||
assert(renderContext->args->hasViewFrustum());
|
assert(renderContext->args->hasViewFrustum());
|
||||||
|
|
||||||
auto config = std::static_pointer_cast<Config>(renderContext->jobConfig);
|
auto config = std::static_pointer_cast<Config>(renderContext->jobConfig);
|
||||||
|
|
||||||
|
const auto& inItems = inputs.get0();
|
||||||
|
const auto& lightingModel = inputs.get1();
|
||||||
|
|
||||||
RenderArgs* args = renderContext->args;
|
RenderArgs* args = renderContext->args;
|
||||||
|
|
||||||
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
gpu::doInBatch(args->_context, [&](gpu::Batch& batch) {
|
||||||
|
@ -264,12 +275,15 @@ DrawOverlay3D::DrawOverlay3D(bool opaque) :
|
||||||
initOverlay3DPipelines(*_shapePlumber);
|
initOverlay3DPipelines(*_shapePlumber);
|
||||||
}
|
}
|
||||||
|
|
||||||
void DrawOverlay3D::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const render::ItemBounds& inItems) {
|
void DrawOverlay3D::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& inputs) {
|
||||||
assert(renderContext->args);
|
assert(renderContext->args);
|
||||||
assert(renderContext->args->hasViewFrustum());
|
assert(renderContext->args->hasViewFrustum());
|
||||||
|
|
||||||
auto config = std::static_pointer_cast<Config>(renderContext->jobConfig);
|
auto config = std::static_pointer_cast<Config>(renderContext->jobConfig);
|
||||||
|
|
||||||
|
const auto& inItems = inputs.get0();
|
||||||
|
const auto& lightingModel = inputs.get1();
|
||||||
|
|
||||||
config->setNumDrawn((int)inItems.size());
|
config->setNumDrawn((int)inItems.size());
|
||||||
emit config->numDrawnChanged();
|
emit config->numDrawnChanged();
|
||||||
|
|
||||||
|
@ -341,10 +355,13 @@ void DrawStencilDeferred::run(const SceneContextPointer& sceneContext, const Ren
|
||||||
args->_batch = nullptr;
|
args->_batch = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
void DrawBackgroundDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const ItemBounds& inItems) {
|
void DrawBackgroundDeferred::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& inputs) {
|
||||||
assert(renderContext->args);
|
assert(renderContext->args);
|
||||||
assert(renderContext->args->hasViewFrustum());
|
assert(renderContext->args->hasViewFrustum());
|
||||||
|
|
||||||
|
const auto& inItems = inputs.get0();
|
||||||
|
const auto& lightingModel = inputs.get1();
|
||||||
|
|
||||||
RenderArgs* args = renderContext->args;
|
RenderArgs* args = renderContext->args;
|
||||||
doInBatch(args->_context, [&](gpu::Batch& batch) {
|
doInBatch(args->_context, [&](gpu::Batch& batch) {
|
||||||
args->_batch = &batch;
|
args->_batch = &batch;
|
||||||
|
|
|
@ -14,6 +14,8 @@
|
||||||
|
|
||||||
#include <gpu/Pipeline.h>
|
#include <gpu/Pipeline.h>
|
||||||
#include <render/CullTask.h>
|
#include <render/CullTask.h>
|
||||||
|
#include "LightingModel.h"
|
||||||
|
|
||||||
|
|
||||||
class DrawConfig : public render::Job::Config {
|
class DrawConfig : public render::Job::Config {
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
@ -37,13 +39,14 @@ protected:
|
||||||
|
|
||||||
class DrawDeferred {
|
class DrawDeferred {
|
||||||
public:
|
public:
|
||||||
|
using Inputs = render::VaryingSet2 <render::ItemBounds, LightingModelPointer>;
|
||||||
using Config = DrawConfig;
|
using Config = DrawConfig;
|
||||||
using JobModel = render::Job::ModelI<DrawDeferred, render::ItemBounds, Config>;
|
using JobModel = render::Job::ModelI<DrawDeferred, Inputs, Config>;
|
||||||
|
|
||||||
DrawDeferred(render::ShapePlumberPointer shapePlumber) : _shapePlumber{ shapePlumber } {}
|
DrawDeferred(render::ShapePlumberPointer shapePlumber) : _shapePlumber{ shapePlumber } {}
|
||||||
|
|
||||||
void configure(const Config& config) { _maxDrawn = config.maxDrawn; }
|
void configure(const Config& config) { _maxDrawn = config.maxDrawn; }
|
||||||
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const render::ItemBounds& inItems);
|
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
render::ShapePlumberPointer _shapePlumber;
|
render::ShapePlumberPointer _shapePlumber;
|
||||||
|
@ -73,13 +76,15 @@ protected:
|
||||||
|
|
||||||
class DrawStateSortDeferred {
|
class DrawStateSortDeferred {
|
||||||
public:
|
public:
|
||||||
|
using Inputs = render::VaryingSet2 <render::ItemBounds, LightingModelPointer>;
|
||||||
|
|
||||||
using Config = DrawStateSortConfig;
|
using Config = DrawStateSortConfig;
|
||||||
using JobModel = render::Job::ModelI<DrawStateSortDeferred, render::ItemBounds, Config>;
|
using JobModel = render::Job::ModelI<DrawStateSortDeferred, Inputs, Config>;
|
||||||
|
|
||||||
DrawStateSortDeferred(render::ShapePlumberPointer shapePlumber) : _shapePlumber{ shapePlumber } {}
|
DrawStateSortDeferred(render::ShapePlumberPointer shapePlumber) : _shapePlumber{ shapePlumber } {}
|
||||||
|
|
||||||
void configure(const Config& config) { _maxDrawn = config.maxDrawn; _stateSort = config.stateSort; }
|
void configure(const Config& config) { _maxDrawn = config.maxDrawn; _stateSort = config.stateSort; }
|
||||||
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const render::ItemBounds& inItems);
|
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
render::ShapePlumberPointer _shapePlumber;
|
render::ShapePlumberPointer _shapePlumber;
|
||||||
|
@ -112,11 +117,13 @@ protected:
|
||||||
|
|
||||||
class DrawBackgroundDeferred {
|
class DrawBackgroundDeferred {
|
||||||
public:
|
public:
|
||||||
|
using Inputs = render::VaryingSet2 <render::ItemBounds, LightingModelPointer>;
|
||||||
|
|
||||||
using Config = DrawBackgroundDeferredConfig;
|
using Config = DrawBackgroundDeferredConfig;
|
||||||
using JobModel = render::Job::ModelI<DrawBackgroundDeferred, render::ItemBounds, Config>;
|
using JobModel = render::Job::ModelI<DrawBackgroundDeferred, Inputs, Config>;
|
||||||
|
|
||||||
void configure(const Config& config) {}
|
void configure(const Config& config) {}
|
||||||
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const render::ItemBounds& inItems);
|
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
gpu::RangeTimer _gpuTimer;
|
gpu::RangeTimer _gpuTimer;
|
||||||
|
@ -142,13 +149,15 @@ protected:
|
||||||
|
|
||||||
class DrawOverlay3D {
|
class DrawOverlay3D {
|
||||||
public:
|
public:
|
||||||
|
using Inputs = render::VaryingSet2 <render::ItemBounds, LightingModelPointer>;
|
||||||
|
|
||||||
using Config = DrawOverlay3DConfig;
|
using Config = DrawOverlay3DConfig;
|
||||||
using JobModel = render::Job::ModelI<DrawOverlay3D, render::ItemBounds, Config>;
|
using JobModel = render::Job::ModelI<DrawOverlay3D, Inputs, Config>;
|
||||||
|
|
||||||
DrawOverlay3D(bool opaque);
|
DrawOverlay3D(bool opaque);
|
||||||
|
|
||||||
void configure(const Config& config) { _maxDrawn = config.maxDrawn; }
|
void configure(const Config& config) { _maxDrawn = config.maxDrawn; }
|
||||||
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const render::ItemBounds& inItems);
|
void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
render::ShapePlumberPointer _shapePlumber;
|
render::ShapePlumberPointer _shapePlumber;
|
||||||
|
|
|
@ -156,10 +156,7 @@ void ToneMappingDeferred::configure(const Config& config) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void ToneMappingDeferred::run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs) {
|
void ToneMappingDeferred::run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext, const Inputs& inputs) {
|
||||||
/* auto framebufferCache = DependencyManager::get<FramebufferCache>();
|
|
||||||
auto lightingBuffer = framebufferCache->getLightingTexture();
|
|
||||||
auto destFbo = framebufferCache->getPrimaryFramebuffer();
|
|
||||||
*/
|
|
||||||
auto lightingBuffer = inputs.get0()->getRenderBuffer(0);
|
auto lightingBuffer = inputs.get0()->getRenderBuffer(0);
|
||||||
auto destFbo = inputs.get1();
|
auto destFbo = inputs.get1();
|
||||||
_toneMappingEffect.render(renderContext->args, lightingBuffer, destFbo);
|
_toneMappingEffect.render(renderContext->args, lightingBuffer, destFbo);
|
||||||
|
|
|
@ -15,7 +15,6 @@
|
||||||
<@include model/Light.slh@>
|
<@include model/Light.slh@>
|
||||||
|
|
||||||
<@include LightingModel.slh@>
|
<@include LightingModel.slh@>
|
||||||
<$declareLightingModel()$>
|
|
||||||
|
|
||||||
<@include LightDirectional.slh@>
|
<@include LightDirectional.slh@>
|
||||||
<$declareLightingDirectional()$>
|
<$declareLightingDirectional()$>
|
||||||
|
|
|
@ -15,7 +15,6 @@
|
||||||
<@include model/Light.slh@>
|
<@include model/Light.slh@>
|
||||||
|
|
||||||
<@include LightingModel.slh@>
|
<@include LightingModel.slh@>
|
||||||
<$declareLightingModel()$>
|
|
||||||
|
|
||||||
<@include LightDirectional.slh@>
|
<@include LightDirectional.slh@>
|
||||||
<$declareLightingDirectional()$>
|
<$declareLightingDirectional()$>
|
||||||
|
@ -40,8 +39,8 @@ vec4 evalGlobalColor(float shadowAttenuation, vec3 position, vec3 normal, vec3 a
|
||||||
vec3 directionalDiffuse;
|
vec3 directionalDiffuse;
|
||||||
vec3 directionalSpecular;
|
vec3 directionalSpecular;
|
||||||
evalLightingDirectional(directionalDiffuse, directionalSpecular, light, fragEyeDir, fragNormal, roughness, metallic, fresnel, albedo, shadowAttenuation);
|
evalLightingDirectional(directionalDiffuse, directionalSpecular, light, fragEyeDir, fragNormal, roughness, metallic, fresnel, albedo, shadowAttenuation);
|
||||||
color += directionalDiffuse * isDiffuseEnabled() * isDirectionalEnabled();
|
color += directionalDiffuse;
|
||||||
color += directionalSpecular * isSpecularEnabled() * isDirectionalEnabled();
|
color += directionalSpecular / opacity;
|
||||||
|
|
||||||
return vec4(color, opacity);
|
return vec4(color, opacity);
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,7 +21,6 @@
|
||||||
<@include model/Light.slh@>
|
<@include model/Light.slh@>
|
||||||
|
|
||||||
<@include LightingModel.slh@>
|
<@include LightingModel.slh@>
|
||||||
<$declareLightingModel()$>
|
|
||||||
|
|
||||||
<@include LightPoint.slh@>
|
<@include LightPoint.slh@>
|
||||||
<$declareLightingPoint(supportScattering)$>
|
<$declareLightingPoint(supportScattering)$>
|
||||||
|
|
|
@ -21,7 +21,6 @@
|
||||||
<@include model/Light.slh@>
|
<@include model/Light.slh@>
|
||||||
|
|
||||||
<@include LightingModel.slh@>
|
<@include LightingModel.slh@>
|
||||||
<$declareLightingModel()$>
|
|
||||||
|
|
||||||
<@include LightSpot.slh@>
|
<@include LightSpot.slh@>
|
||||||
<$declareLightingSpot(supportScattering)$>
|
<$declareLightingSpot(supportScattering)$>
|
||||||
|
|
|
@ -51,6 +51,7 @@ void ShapePlumber::addPipeline(const Key& key, const gpu::ShaderPointer& program
|
||||||
void ShapePlumber::addPipeline(const Filter& filter, const gpu::ShaderPointer& program, const gpu::StatePointer& state,
|
void ShapePlumber::addPipeline(const Filter& filter, const gpu::ShaderPointer& program, const gpu::StatePointer& state,
|
||||||
BatchSetter batchSetter) {
|
BatchSetter batchSetter) {
|
||||||
gpu::Shader::BindingSet slotBindings;
|
gpu::Shader::BindingSet slotBindings;
|
||||||
|
slotBindings.insert(gpu::Shader::Binding(std::string("lightingModelBuffer"), Slot::BUFFER::LIGHTING_MODEL));
|
||||||
slotBindings.insert(gpu::Shader::Binding(std::string("skinClusterBuffer"), Slot::BUFFER::SKINNING));
|
slotBindings.insert(gpu::Shader::Binding(std::string("skinClusterBuffer"), Slot::BUFFER::SKINNING));
|
||||||
slotBindings.insert(gpu::Shader::Binding(std::string("materialBuffer"), Slot::BUFFER::MATERIAL));
|
slotBindings.insert(gpu::Shader::Binding(std::string("materialBuffer"), Slot::BUFFER::MATERIAL));
|
||||||
slotBindings.insert(gpu::Shader::Binding(std::string("texMapArrayBuffer"), Slot::BUFFER::TEXMAPARRAY));
|
slotBindings.insert(gpu::Shader::Binding(std::string("texMapArrayBuffer"), Slot::BUFFER::TEXMAPARRAY));
|
||||||
|
@ -79,6 +80,7 @@ void ShapePlumber::addPipeline(const Filter& filter, const gpu::ShaderPointer& p
|
||||||
locations->metallicTextureUnit = program->getTextures().findLocation("metallicMap");
|
locations->metallicTextureUnit = program->getTextures().findLocation("metallicMap");
|
||||||
locations->emissiveTextureUnit = program->getTextures().findLocation("emissiveMap");
|
locations->emissiveTextureUnit = program->getTextures().findLocation("emissiveMap");
|
||||||
locations->occlusionTextureUnit = program->getTextures().findLocation("occlusionMap");
|
locations->occlusionTextureUnit = program->getTextures().findLocation("occlusionMap");
|
||||||
|
locations->lightingModelBufferUnit = program->getBuffers().findLocation("lightingModelBuffer");
|
||||||
locations->skinClusterBufferUnit = program->getBuffers().findLocation("skinClusterBuffer");
|
locations->skinClusterBufferUnit = program->getBuffers().findLocation("skinClusterBuffer");
|
||||||
locations->materialBufferUnit = program->getBuffers().findLocation("materialBuffer");
|
locations->materialBufferUnit = program->getBuffers().findLocation("materialBuffer");
|
||||||
locations->texMapArrayBufferUnit = program->getBuffers().findLocation("texMapArrayBuffer");
|
locations->texMapArrayBufferUnit = program->getBuffers().findLocation("texMapArrayBuffer");
|
||||||
|
|
|
@ -196,10 +196,11 @@ public:
|
||||||
class Slot {
|
class Slot {
|
||||||
public:
|
public:
|
||||||
enum BUFFER {
|
enum BUFFER {
|
||||||
SKINNING = 2,
|
SKINNING = 0,
|
||||||
MATERIAL,
|
MATERIAL,
|
||||||
TEXMAPARRAY,
|
TEXMAPARRAY,
|
||||||
LIGHT
|
LIGHTING_MODEL,
|
||||||
|
LIGHT,
|
||||||
};
|
};
|
||||||
|
|
||||||
enum MAP {
|
enum MAP {
|
||||||
|
@ -225,6 +226,7 @@ public:
|
||||||
int emissiveTextureUnit;
|
int emissiveTextureUnit;
|
||||||
int occlusionTextureUnit;
|
int occlusionTextureUnit;
|
||||||
int normalFittingMapUnit;
|
int normalFittingMapUnit;
|
||||||
|
int lightingModelBufferUnit;
|
||||||
int skinClusterBufferUnit;
|
int skinClusterBufferUnit;
|
||||||
int materialBufferUnit;
|
int materialBufferUnit;
|
||||||
int texMapArrayBufferUnit;
|
int texMapArrayBufferUnit;
|
||||||
|
|
|
@ -83,8 +83,6 @@ protected:
|
||||||
};
|
};
|
||||||
|
|
||||||
using VaryingPairBase = std::pair<Varying, Varying>;
|
using VaryingPairBase = std::pair<Varying, Varying>;
|
||||||
|
|
||||||
|
|
||||||
template < typename T0, typename T1 >
|
template < typename T0, typename T1 >
|
||||||
class VaryingSet2 : public VaryingPairBase {
|
class VaryingSet2 : public VaryingPairBase {
|
||||||
public:
|
public:
|
||||||
|
@ -110,6 +108,7 @@ public:
|
||||||
}
|
}
|
||||||
virtual uint8_t length() const { return 2; }
|
virtual uint8_t length() const { return 2; }
|
||||||
|
|
||||||
|
Varying hasVarying() const { return Varying((*this)); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -142,6 +141,7 @@ public:
|
||||||
}
|
}
|
||||||
virtual uint8_t length() const { return 3; }
|
virtual uint8_t length() const { return 3; }
|
||||||
|
|
||||||
|
Varying hasVarying() const { return Varying((*this)); }
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class T0, class T1, class T2, class T3>
|
template <class T0, class T1, class T2, class T3>
|
||||||
|
@ -178,6 +178,7 @@ public:
|
||||||
}
|
}
|
||||||
virtual uint8_t length() const { return 4; }
|
virtual uint8_t length() const { return 4; }
|
||||||
|
|
||||||
|
Varying hasVarying() const { return Varying((*this)); }
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -204,6 +205,8 @@ public:
|
||||||
|
|
||||||
const T4& get4() const { return std::get<4>((*this)).template get<T4>(); }
|
const T4& get4() const { return std::get<4>((*this)).template get<T4>(); }
|
||||||
T4& edit4() { return std::get<4>((*this)).template edit<T4>(); }
|
T4& edit4() { return std::get<4>((*this)).template edit<T4>(); }
|
||||||
|
|
||||||
|
Varying hasVarying() const { return Varying((*this)); }
|
||||||
};
|
};
|
||||||
|
|
||||||
template <class T0, class T1, class T2, class T3, class T4, class T5>
|
template <class T0, class T1, class T2, class T3, class T4, class T5>
|
||||||
|
@ -232,6 +235,8 @@ public:
|
||||||
|
|
||||||
const T5& get5() const { return std::get<5>((*this)).template get<T5>(); }
|
const T5& get5() const { return std::get<5>((*this)).template get<T5>(); }
|
||||||
T5& edit5() { return std::get<5>((*this)).template edit<T5>(); }
|
T5& edit5() { return std::get<5>((*this)).template edit<T5>(); }
|
||||||
|
|
||||||
|
Varying hasVarying() const { return Varying((*this)); }
|
||||||
};
|
};
|
||||||
|
|
||||||
template < class T, int NUM >
|
template < class T, int NUM >
|
||||||
|
|
|
@ -22,7 +22,6 @@ Column {
|
||||||
Repeater {
|
Repeater {
|
||||||
model: [
|
model: [
|
||||||
"Unlit:LightingModel:enableUnlit",
|
"Unlit:LightingModel:enableUnlit",
|
||||||
"Shaded:LightingModel:enableShaded",
|
|
||||||
"Emissive:LightingModel:enableEmissive",
|
"Emissive:LightingModel:enableEmissive",
|
||||||
"Lightmap:LightingModel:enableLightmap",
|
"Lightmap:LightingModel:enableLightmap",
|
||||||
]
|
]
|
||||||
|
@ -68,6 +67,19 @@ Column {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Column {
|
||||||
|
spacing: 10
|
||||||
|
Repeater {
|
||||||
|
model: [
|
||||||
|
"Light Contour:LightingModel:showLightContour"
|
||||||
|
]
|
||||||
|
CheckBox {
|
||||||
|
text: modelData.split(":")[0]
|
||||||
|
checked: Render.getConfig(modelData.split(":")[1])
|
||||||
|
onCheckedChanged: { Render.getConfig(modelData.split(":")[1])[modelData.split(":")[2]] = checked }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
Column {
|
Column {
|
||||||
spacing: 10
|
spacing: 10
|
||||||
|
|
Loading…
Reference in a new issue