Loading [MathJax]/extensions/TeX/AMSsymbols.js
Radium Engine  1.6.3
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
RenderTechnique.cpp
1#include <Core/Utils/Log.hpp>
2#include <Engine/Data/BlinnPhongMaterial.hpp>
3#include <Engine/Data/RenderParameters.hpp>
4#include <Engine/Data/ShaderProgramManager.hpp>
5#include <Engine/RadiumEngine.hpp>
6#include <Engine/Rendering/RenderTechnique.hpp>
7#include <algorithm>
8#include <cstddef>
9#include <map>
10#include <ostream>
11#include <type_traits>
12
13namespace Ra {
14namespace Engine {
15namespace Rendering {
16
17using namespace Core::Utils; // log
18
19std::shared_ptr<Ra::Engine::Rendering::RenderTechnique> RadiumDefaultRenderTechnique { nullptr };
20
21RenderTechnique::RenderTechnique() : m_numActivePass { 0 } {
22 for ( auto p = Index( 0 ); p < s_maxNbPasses; ++p ) {
23 m_activePasses[p] = PassConfiguration( Data::ShaderConfiguration(), nullptr );
24 m_passesParameters[p] = nullptr;
25 }
26}
27
28RenderTechnique::RenderTechnique( const RenderTechnique& o ) :
29 m_numActivePass { o.m_numActivePass },
30 m_dirtyBits { o.m_dirtyBits },
31 m_setPasses { o.m_setPasses } {
32 for ( auto p = Index( 0 ); p < m_numActivePass; ++p ) {
33 if ( hasConfiguration( p ) ) {
34 m_activePasses[p] = o.m_activePasses[p];
35 m_passesParameters[p] = o.m_passesParameters[p];
36 }
37 }
38}
39
40RenderTechnique::~RenderTechnique() = default;
41
43 Core::Utils::Index pass ) {
44 m_numActivePass = std::max( m_numActivePass, pass + 1 );
45 m_activePasses[pass] = PassConfiguration( newConfig, nullptr );
46 setDirty( pass );
47 setConfiguration( pass );
48}
49
50const Data::ShaderProgram* RenderTechnique::getShader( Core::Utils::Index pass ) const {
51 if ( hasConfiguration( pass ) ) { return m_activePasses[pass].second; }
52 return nullptr;
53}
54
57 Core::Utils::Index pass ) {
58 if ( m_numActivePass == 0 ) {
59 LOG( logERROR )
60 << "Unable to set pass parameters : is passes configured using setConfiguration ? ";
61 return;
62 }
63 if ( pass.isValid() ) {
64 if ( hasConfiguration( pass ) ) { m_passesParameters[pass] = provider; }
65 }
66 else {
67 for ( int i = 0; i < m_numActivePass; ++i ) {
68 if ( hasConfiguration( i ) ) { m_passesParameters[i] = provider; }
69 }
70 }
71 // add the provider specific properties to the configuration
72 addPassProperties( provider->getPropertyList(), pass );
73}
74
76 Core::Utils::Index pass ) {
77 if ( m_numActivePass == 0 ) {
78 LOG( logERROR )
79 << "Unable to set pass properties : is passes configured using setConfiguration ? ";
80 return;
81 }
82 if ( pass.isValid() && hasConfiguration( pass ) ) {
83 m_activePasses[pass].first.addProperties( props );
84 setDirty( pass );
85 }
86 else {
87 for ( int i = 0; i < m_numActivePass; ++i ) {
88 if ( hasConfiguration( i ) ) {
89 m_activePasses[i].first.addProperties( props );
90 setDirty( i );
91 }
92 }
93 }
94}
95
97RenderTechnique::getParametersProvider( Core::Utils::Index pass ) const {
98 if ( hasConfiguration( pass ) ) { return m_passesParameters[pass].get(); }
99 return nullptr;
100}
101
103 auto shaderProgramManager = RadiumEngine::getInstance()->getShaderProgramManager();
104
105 for ( auto p = Index( 0 ); p < m_numActivePass; ++p ) {
106 if ( hasConfiguration( p ) &&
107 ( ( nullptr == m_activePasses[p].second ) || isDirty( p ) ) ) {
108 m_activePasses[p].second =
109 shaderProgramManager->getShaderProgram( m_activePasses[p].first );
110 clearDirty( p );
111 }
112 }
113 for ( auto p = Index( 0 ); p < m_numActivePass; ++p ) {
114 if ( m_passesParameters[p] ) { m_passesParameters[p]->updateGL(); }
115 }
116}
117
120 if ( RadiumDefaultRenderTechnique != nullptr ) {
121 return *( RadiumDefaultRenderTechnique.get() );
122 }
124 auto rt = new RenderTechnique;
125 auto builder = EngineRenderTechniques::getDefaultTechnique( "BlinnPhong" );
126 if ( !builder.first ) {
127 LOG( logERROR ) << "Unable to create the default technique : is the Engine initialized ? ";
128 }
129 builder.second( *rt, false );
130 rt->setParametersProvider( mat );
131 RadiumDefaultRenderTechnique.reset( rt );
132 return *( RadiumDefaultRenderTechnique.get() );
133}
134
138namespace EngineRenderTechniques {
139
141static std::map<std::string, DefaultTechniqueBuilder> EngineTechniqueRegistry;
142
146bool registerDefaultTechnique( const std::string& name, DefaultTechniqueBuilder builder ) {
147 auto result = EngineTechniqueRegistry.insert( { name, builder } );
148 return result.second;
149}
150
154bool removeDefaultTechnique( const std::string& name ) {
155 std::size_t removed = EngineTechniqueRegistry.erase( name );
156 return ( removed == 1 );
157}
158
164std::pair<bool, DefaultTechniqueBuilder> getDefaultTechnique( const std::string& name ) {
165 auto search = EngineTechniqueRegistry.find( name );
166 if ( search != EngineTechniqueRegistry.end() ) { return { true, search->second }; }
167 auto result = std::make_pair( false, [name]( RenderTechnique&, bool ) -> void {
168 LOG( logERROR ) << "Undefined default technique for " << name << " !";
169 } );
170 return result;
171}
172
173bool cleanup() {
174 EngineTechniqueRegistry.clear();
175 return true;
176}
177
178} // namespace EngineRenderTechniques
179
180} // namespace Rendering
181} // namespace Engine
182} // namespace Ra
Shader program parameter provider.
void setParametersProvider(std::shared_ptr< Data::ShaderParameterProvider > provider, Core::Utils::Index pass=Core::Utils::Index(-1))
void clearDirty(Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE)
void setConfiguration(const Data::ShaderConfiguration &newConfig, Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE)
const Data::ShaderParameterProvider * getParametersProvider(Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE) const
void addPassProperties(const std::list< std::string > &props, Core::Utils::Index pass=Core::Utils::Index {})
static RenderTechnique createDefaultRenderTechnique()
const Data::ShaderProgram * getShader(Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE) const
bool hasConfiguration(Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE) const
bool isDirty(Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE) const
void setDirty(Core::Utils::Index pass=DefaultRenderingPasses::LIGHTING_OPAQUE)
T get(T... args)
T make_pair(T... args)
T max(T... args)
hepler function to manage enum as underlying types in VariableSet
Definition Cage.cpp:4
T reset(T... args)