2 * Copyright (c) 2018 Samsung Electronics Co., Ltd.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
19 #include <dali/internal/render/shaders/program-controller.h>
22 #include <dali/integration-api/gl-defines.h>
23 #include <dali/internal/common/shader-saver.h>
24 #include <dali/internal/render/gl-resources/gl-call-debug.h>
25 #include <dali/internal/render/shaders/program.h>
33 ProgramController::ProgramController( Integration::GlAbstraction& glAbstraction )
34 : mShaderSaver( nullptr ),
35 mGlAbstraction( glAbstraction ),
36 mCurrentProgram( nullptr ),
37 mProgramBinaryFormat( 0 ),
38 mNumberOfProgramBinaryFormats( 0 )
40 // we have 17 default programs so make room for those and a few custom ones as well
41 mProgramCache.Reserve( 32 );
44 ProgramController::~ProgramController() = default;
46 void ProgramController::ResetProgramMatrices()
48 const ProgramIterator end = mProgramCache.End();
49 for ( ProgramIterator iter = mProgramCache.Begin(); iter != end; ++iter )
51 Program* program = (*iter)->GetProgram();
52 program->SetProjectionMatrix( nullptr );
53 program->SetViewMatrix( nullptr );
57 void ProgramController::GlContextCreated()
59 // reset any potential previous errors
60 LOG_GL( "GetError()\n" );
61 CHECK_GL( mGlAbstraction, mGlAbstraction.GetError() );
63 // find out if program binaries are supported and the format enum as well
64 Dali::Vector<GLint> programBinaryFormats;
66 CHECK_GL( mGlAbstraction, mGlAbstraction.GetIntegerv(GL_NUM_PROGRAM_BINARY_FORMATS_OES, &mNumberOfProgramBinaryFormats ) );
67 LOG_GL("GetIntegerv(GL_NUM_PROGRAM_BINARY_FORMATS_OES) = %d\n", mNumberOfProgramBinaryFormats );
69 if( GL_NO_ERROR == mGlAbstraction.GetError() && 0 < mNumberOfProgramBinaryFormats )
71 programBinaryFormats.Resize( mNumberOfProgramBinaryFormats );
72 CHECK_GL( mGlAbstraction, mGlAbstraction.GetIntegerv(GL_PROGRAM_BINARY_FORMATS_OES, &programBinaryFormats[0] ) );
73 LOG_GL("GetIntegerv(GL_PROGRAM_BINARY_FORMATS_OES) = %d\n", programBinaryFormats[0] );
74 mProgramBinaryFormat = programBinaryFormats[0];
78 void ProgramController::GlContextDestroyed()
80 mNumberOfProgramBinaryFormats = 0;
81 mProgramBinaryFormat = 0;
83 SetCurrentProgram( nullptr );
84 // Inform programs they are no longer valid
85 const ProgramIterator end = mProgramCache.End();
86 for ( ProgramIterator iter = mProgramCache.Begin(); iter != end; ++iter )
88 (*iter)->GetProgram()->GlContextDestroyed();
92 Integration::GlAbstraction& ProgramController::GetGlAbstraction()
94 return mGlAbstraction;
97 Program* ProgramController::GetProgram( size_t shaderHash )
99 Program* program = nullptr;
100 const ProgramIterator end = mProgramCache.End();
101 for ( ProgramIterator iter = mProgramCache.Begin(); iter != end; ++iter )
103 size_t hash = (*iter)->GetHash();
104 if( shaderHash == hash )
106 program = (*iter)->GetProgram();
113 void ProgramController::AddProgram( size_t shaderHash, Program* program )
115 // we expect unique hash values so its event thread sides job to guarantee that
116 // AddProgram is only called after program checks that GetProgram returns NULL
117 mProgramCache.PushBack( new ProgramPair( program, shaderHash ) );
120 Program* ProgramController::GetCurrentProgram()
122 return mCurrentProgram;
125 void ProgramController::SetCurrentProgram( Program* program )
127 mCurrentProgram = program;
130 bool ProgramController::IsBinarySupported()
132 return mNumberOfProgramBinaryFormats > 0;
135 GLenum ProgramController::ProgramBinaryFormat()
137 return mProgramBinaryFormat;
140 void ProgramController::StoreBinary( Internal::ShaderDataPtr programData )
142 DALI_ASSERT_DEBUG( programData->GetBufferSize() > 0 );
143 DALI_ASSERT_DEBUG( mShaderSaver && "SetShaderSaver() should have been called during startup." );
145 if( mShaderSaver != nullptr )
147 mShaderSaver->SaveBinary( programData );
151 void ProgramController::SetShaderSaver( ShaderSaver& shaderSaver )
153 mShaderSaver = &shaderSaver;
156 void ProgramController::ClearCurrentProgram()
158 SetCurrentProgram( nullptr );
161 } // namespace Internal