2 * Copyright (c) 2016 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.
18 #include "scene-graph-texture-set.h"
21 #include <dali/integration-api/resource-declarations.h>
22 #include <dali/internal/common/internal-constants.h>
23 #include <dali/internal/update/resources/texture-metadata.h>
24 #include <dali/internal/update/resources/resource-manager.h>
25 #include <dali/internal/common/memory-pool-object-allocator.h>
26 #include <dali/internal/update/rendering/scene-graph-renderer.h>
28 namespace //Unnamed namespace
30 //Memory pool used to allocate new texture sets. Memory used by this pool will be released when shutting down DALi
31 Dali::Internal::MemoryPoolObjectAllocator<Dali::Internal::SceneGraph::TextureSet> gTextureSetMemoryPool;
43 TextureSet* TextureSet::New()
45 return new ( gTextureSetMemoryPool.AllocateRawThreadSafe() ) TextureSet();
48 TextureSet::TextureSet()
52 mResourcesReady( true ),
53 mFinishedResourceAcquisition( true ),
59 TextureSet::~TextureSet()
61 size_t rendererCount = mRenderers.Size();
62 for( size_t i(0); i<rendererCount; ++i )
64 mRenderers[i]->TextureSetDeleted();
68 void TextureSet::operator delete( void* ptr )
70 gTextureSetMemoryPool.FreeThreadSafe( static_cast<TextureSet*>( ptr ) );
73 void TextureSet::Prepare( const ResourceManager& resourceManager )
75 if( mChanged && mTextures.Empty() )
77 unsigned int opaqueCount = 0;
78 unsigned int completeCount = 0;
79 unsigned int failedCount = 0;
80 unsigned int frameBufferCount = 0;
81 const std::size_t textureCount( mTextureId.Count() );
82 if( textureCount > 0 )
84 for( unsigned int i(0); i<textureCount; ++i )
86 const ResourceId textureId = mTextureId[ i ];
87 TextureMetadata* metadata = NULL;
88 if( textureId != Integration::InvalidResourceId )
90 // if there is metadata, resource is loaded
91 if( resourceManager.GetTextureMetadata( textureId, metadata ) )
93 DALI_ASSERT_DEBUG( metadata );
94 // metadata is valid pointer from now on
95 if( metadata->IsFullyOpaque() )
100 if( metadata->IsFramebuffer() )
102 if( metadata->HasFrameBufferBeenRenderedTo() )
113 // loaded so will complete this frame
116 // no point checking failure as there is no metadata for failed loads
118 // if no metadata, loading can be failed
119 else if( resourceManager.HasResourceLoadFailed( textureId ) )
126 //If the texture is not valid it is considerer opaque and complete
133 mHasAlpha = ( opaqueCount != textureCount );
135 // ready for rendering when all textures are either successfully loaded or they are FBOs
136 mResourcesReady = (completeCount + frameBufferCount >= textureCount);
138 // Texture set is complete if all resources are either loaded or failed or, if they are FBOs have been rendererd to
139 mFinishedResourceAcquisition = ( completeCount + failedCount == textureCount );
141 if( mFinishedResourceAcquisition )
143 // Texture set is now considered not changed
149 void TextureSet::SetImage( size_t index, ResourceId imageId )
151 size_t textureCount( mTextureId.Size() );
152 if( textureCount < index + 1 )
154 mTextureId.Resize( index + 1 );
155 mSamplers.Resize( index + 1 );
156 for( size_t i(textureCount); i<=index; ++i )
158 mTextureId[i] = Integration::InvalidResourceId;
163 mTextureId[index] = imageId;
165 NotifyChangeToRenderers();
168 void TextureSet::SetSampler( size_t index, Render::Sampler* sampler )
170 size_t samplerCount( mSamplers.Size() );
171 if( samplerCount < index + 1 )
173 mSamplers.Resize( index + 1 );
174 mTextureId.Resize( index + 1 );
175 for( size_t i(samplerCount); i<=index; ++i )
177 mTextureId[i] = Integration::InvalidResourceId;
182 mSamplers[index] = sampler;
183 NotifyChangeToRenderers();
186 void TextureSet::SetTexture( size_t index, Render::NewTexture* texture )
188 const size_t textureCount( mTextures.Size() );
189 if( textureCount < index + 1 )
191 mTextures.Resize( index + 1 );
192 mSamplers.Resize( index + 1 );
194 for( size_t i(textureCount); i<=index; ++i )
201 mTextures[index] = texture;
202 mHasAlpha |= texture->HasAlphaChannel();
203 NotifyChangeToRenderers();
206 bool TextureSet::HasAlpha() const
211 void TextureSet::GetResourcesStatus( bool& resourcesReady, bool& finishedResourceAcquisition )
213 resourcesReady = mResourcesReady;
214 finishedResourceAcquisition = mFinishedResourceAcquisition;
217 void TextureSet::AddObserver( Renderer* renderer )
219 size_t rendererCount( mRenderers.Size() );
220 for( size_t i(0); i<rendererCount; ++i )
222 if( mRenderers[i] == renderer )
224 //Renderer already in the list
229 mRenderers.PushBack( renderer );
232 void TextureSet::RemoveObserver( Renderer* renderer )
234 size_t rendererCount( mRenderers.Size() );
235 for( size_t i(0); i<rendererCount; ++i )
237 if( mRenderers[i] == renderer )
239 mRenderers.Remove( mRenderers.Begin() + i );
245 void TextureSet::NotifyChangeToRenderers()
247 size_t rendererCount = mRenderers.Size();
248 for( size_t i(0); i<rendererCount; ++i )
250 mRenderers[i]->TextureSetChanged();
254 } // namespace SceneGraph
256 } // namespace Internal