From f7cb2ec85baaf41cffa3ff4e050680e5059d443c Mon Sep 17 00:00:00 2001 From: Zach Pomerantz Date: Tue, 3 Jan 2017 20:41:57 -0500 Subject: [PATCH] add plain forward model shaders --- .../render-utils/src/RenderForwardTask.cpp | 42 ++++++++++++++++++- .../render-utils/src/RenderForwardTask.h | 11 +++++ .../render-utils/src/RenderPipelines.cpp | 16 +++++++ libraries/render-utils/src/nop.slf | 16 +++++++ 4 files changed, 84 insertions(+), 1 deletion(-) create mode 100644 libraries/render-utils/src/nop.slf diff --git a/libraries/render-utils/src/RenderForwardTask.cpp b/libraries/render-utils/src/RenderForwardTask.cpp index ebc9ac5b94..c7a3433c96 100755 --- a/libraries/render-utils/src/RenderForwardTask.cpp +++ b/libraries/render-utils/src/RenderForwardTask.cpp @@ -26,12 +26,15 @@ #include #include +#include "nop_frag.h" using namespace render; +extern void initForwardPipelines(ShapePlumber& plumber); RenderForwardTask::RenderForwardTask(RenderFetchCullSortTask::Output items) { // Prepare the ShapePipelines ShapePlumberPointer shapePlumber = std::make_shared(); + initForwardPipelines(*shapePlumber); // Extract opaques / transparents / lights / overlays const auto opaques = items[0]; @@ -44,9 +47,10 @@ RenderForwardTask::RenderForwardTask(RenderFetchCullSortTask::Output items) { const auto framebuffer = addJob("PrepareFramebuffer"); addJob("DrawOpaques", opaques, shapePlumber); + addJob("Stencil"); addJob("DrawBackground", background); - // bounds do not draw on stencil buffer, so they must come last + // Bounds do not draw on stencil buffer, so they must come last addJob("DrawBounds", opaques); // Blit! @@ -116,6 +120,42 @@ void Draw::run(const SceneContextPointer& sceneContext, const RenderContextPoint args->_batch = nullptr; } +const gpu::PipelinePointer Stencil::getPipeline() { + if (!_stencilPipeline) { + auto vs = gpu::StandardShaderLib::getDrawUnitQuadTexcoordVS(); + auto ps = gpu::Shader::createPixel(std::string(nop_frag)); + gpu::ShaderPointer program = gpu::Shader::createProgram(vs, ps); + gpu::Shader::makeProgram(*program); + + auto state = std::make_shared(); + state->setDepthTest(true, false, gpu::LESS_EQUAL); + const gpu::int8 STENCIL_OPAQUE = 1; + state->setStencilTest(true, 0xFF, gpu::State::StencilTest(STENCIL_OPAQUE, 0xFF, gpu::ALWAYS, + gpu::State::STENCIL_OP_REPLACE, + gpu::State::STENCIL_OP_REPLACE, + gpu::State::STENCIL_OP_KEEP)); + + _stencilPipeline = gpu::Pipeline::create(program, state); + } + return _stencilPipeline; +} + +void Stencil::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext) { + RenderArgs* args = renderContext->args; + + gpu::doInBatch(args->_context, [&](gpu::Batch& batch) { + args->_batch = &batch; + + batch.enableStereo(false); + batch.setViewportTransform(args->_viewport); + batch.setStateScissorRect(args->_viewport); + + batch.setPipeline(getPipeline()); + batch.draw(gpu::TRIANGLE_STRIP, 4); + }); + args->_batch = nullptr; +} + void DrawBackground::run(const SceneContextPointer& sceneContext, const RenderContextPointer& renderContext, const Inputs& background) { RenderArgs* args = renderContext->args; diff --git a/libraries/render-utils/src/RenderForwardTask.h b/libraries/render-utils/src/RenderForwardTask.h index 5f9386ceba..a957f7493e 100755 --- a/libraries/render-utils/src/RenderForwardTask.h +++ b/libraries/render-utils/src/RenderForwardTask.h @@ -48,6 +48,17 @@ private: render::ShapePlumberPointer _shapePlumber; }; +class Stencil { +public: + using JobModel = render::Job::Model; + + void run(const render::SceneContextPointer& sceneContext, const render::RenderContextPointer& renderContext); + +private: + const gpu::PipelinePointer getPipeline(); + gpu::PipelinePointer _stencilPipeline; +}; + class DrawBackground { public: using Inputs = render::ItemBounds; diff --git a/libraries/render-utils/src/RenderPipelines.cpp b/libraries/render-utils/src/RenderPipelines.cpp index d28e1aa0a2..2f04d778e2 100644 --- a/libraries/render-utils/src/RenderPipelines.cpp +++ b/libraries/render-utils/src/RenderPipelines.cpp @@ -53,6 +53,7 @@ using namespace std::placeholders; void initOverlay3DPipelines(ShapePlumber& plumber); void initDeferredPipelines(ShapePlumber& plumber); +void initForwardPipelines(ShapePlumber& plumber); void addPlumberPipeline(ShapePlumber& plumber, const ShapeKey& key, const gpu::ShaderPointer& vertex, const gpu::ShaderPointer& pixel); @@ -218,6 +219,21 @@ void initDeferredPipelines(render::ShapePlumber& plumber) { skinModelShadowVertex, modelShadowPixel); } +void initForwardPipelines(render::ShapePlumber& plumber) { + // Vertex shaders + auto modelVertex = gpu::Shader::createVertex(std::string(model_vert)); + + // Pixel shaders + auto modelPixel = gpu::Shader::createPixel(std::string(model_frag)); + + using Key = render::ShapeKey; + auto addPipeline = std::bind(&addPlumberPipeline, std::ref(plumber), _1, _2, _3); + // Opaques + addPipeline( + Key::Builder(), + modelVertex, modelPixel); + } + void addPlumberPipeline(ShapePlumber& plumber, const ShapeKey& key, const gpu::ShaderPointer& vertex, const gpu::ShaderPointer& pixel) { // These key-values' pipelines are added by this functor in addition to the key passed diff --git a/libraries/render-utils/src/nop.slf b/libraries/render-utils/src/nop.slf new file mode 100644 index 0000000000..f87db4e138 --- /dev/null +++ b/libraries/render-utils/src/nop.slf @@ -0,0 +1,16 @@ +<@include gpu/Config.slh@> +<$VERSION_HEADER$> +// Generated on <$_SCRIBE_DATE$> +// +// nop.frag +// fragment shader +// +// Created by Zach Pomerantz on 1/3/2017. +// Copyright 2017 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +void main(void) { +}