ResourceImage/Image split
[platform/core/uifw/dali-core.git] / dali / internal / event / images / atlas-impl.cpp
1 /*
2  * Copyright (c) 2015 Samsung Electronics Co., Ltd.
3  *
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
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
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.
15  *
16  */
17
18 // CLASS HEADER
19 #include <dali/internal/event/images/atlas-impl.h>
20
21 // INTERNAL INCLUDES
22 #include <dali/public-api/object/type-registry.h>
23 #include <dali/internal/event/common/thread-local-storage.h>
24 #include <dali/internal/event/images/bitmap-image-impl.h>
25 #include <dali/internal/event/resources/resource-client.h>
26 #include <dali/integration-api/bitmap.h>
27
28 namespace Dali
29 {
30
31 namespace Internal
32 {
33
34 namespace
35 {
36 TypeRegistration mType( typeid( Dali::Atlas ), typeid( Dali::Image ), NULL );
37 }
38
39 Atlas* Atlas::New( std::size_t width,
40                    std::size_t height,
41                    Pixel::Format pixelFormat )
42 {
43   return new Atlas( width, height, pixelFormat );
44 }
45
46 bool Atlas::Upload( const BitmapImage& bitmapImage,
47                     std::size_t xOffset,
48                     std::size_t yOffset )
49 {
50   bool uploadSuccess( false );
51
52   AllocateAtlas();
53
54   if( IsWithin(bitmapImage, xOffset, yOffset) )
55   {
56     ResourceId destId = GetResourceId();
57     ResourceId srcId = bitmapImage.GetResourceId();
58
59     if( destId && srcId )
60     {
61       mResourceClient.UploadBitmap( destId, srcId, xOffset, yOffset );
62       uploadSuccess = true;
63     }
64   }
65
66   return uploadSuccess;
67 }
68
69 Atlas::~Atlas()
70 {
71   ReleaseAtlas();
72 }
73
74 Atlas::Atlas( std::size_t width,
75               std::size_t height,
76               Pixel::Format pixelFormat )
77 : mResourceClient( ThreadLocalStorage::Get().GetResourceClient() ),
78   mPixelFormat( pixelFormat )
79 {
80   mWidth  = width;
81   mHeight = height;
82 }
83
84 void Atlas::Connect()
85 {
86   ++mConnectionCount;
87
88   if( mConnectionCount == 1 )
89   {
90     AllocateAtlas();
91   }
92 }
93
94 void Atlas::Disconnect()
95 {
96   if( mConnectionCount )
97   {
98     --mConnectionCount;
99
100     if ( Dali::Image::UNUSED == mReleasePolicy &&
101          mConnectionCount == 0 )
102     {
103       ReleaseAtlas();
104     }
105   }
106 }
107
108 bool Atlas::IsWithin( const BitmapImage& bitmapImage,
109                       std::size_t xOffset,
110                       std::size_t yOffset )
111 {
112   bool within(false);
113
114   if( mPixelFormat != bitmapImage.GetPixelFormat() )
115   {
116     DALI_LOG_ERROR( "Pixel format %d does not match Atlas format %d\n", bitmapImage.GetPixelFormat(), mPixelFormat );
117   }
118   else
119   {
120     const unsigned int width  = bitmapImage.GetWidth();
121     const unsigned int height = bitmapImage.GetHeight();
122
123     if( xOffset < mWidth  &&
124         yOffset < mHeight &&
125         xOffset+width  <= mWidth &&
126         yOffset+height <= mHeight )
127     {
128       within = true;
129     }
130     else
131     {
132       DALI_LOG_ERROR( "%dx%d image does not fit at offset %d,%d\n", width, height, xOffset, yOffset );
133     }
134   }
135
136   return within;
137 }
138
139 void Atlas::AllocateAtlas()
140 {
141   if( !mTicket )
142   {
143     mTicket = mResourceClient.AllocateTexture( mWidth, mHeight, mPixelFormat );
144   }
145 }
146
147 void Atlas::ReleaseAtlas()
148 {
149   mTicket.Reset();
150 }
151
152 } // namespace Internal
153
154 } // namespace Dali