Fix premultiplied alpha issue
[platform/core/uifw/dali-toolkit.git] / dali-toolkit / internal / image-loader / image-load-thread.h
1 #ifndef DALI_TOOLKIT_IMAGE_LOAD_THREAD_H
2 #define DALI_TOOLKIT_IMAGE_LOAD_THREAD_H
3
4 /*
5  * Copyright (c) 2019 Samsung Electronics Co., Ltd.
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  * http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  */
19
20 // EXTERNAL INCLUDES
21 #include <dali/public-api/common/dali-vector.h>
22 #include <dali/public-api/object/ref-object.h>
23 #include <dali/public-api/images/image-operations.h>
24 #include <dali/devel-api/threading/conditional-wait.h>
25 #include <dali/devel-api/threading/mutex.h>
26 #include <dali/devel-api/threading/thread.h>
27 #include <dali/devel-api/adaptor-framework/event-thread-callback.h>
28 #include <dali/devel-api/adaptor-framework/pixel-buffer.h>
29 #include <dali-toolkit/internal/visuals/visual-url.h>
30 #include <dali-toolkit/devel-api/image-loader/async-image-loader-devel.h>
31 #include <dali/integration-api/adaptor-framework/log-factory-interface.h>
32
33 namespace Dali
34 {
35
36 namespace Toolkit
37 {
38
39 namespace Internal
40 {
41
42 /**
43  * The task of loading and packing an image into the atlas.
44  */
45 struct LoadingTask
46 {
47   /**
48    * Constructor.
49    * @param [in] id of the task
50    * @param [in] url The URL of the image file to load.
51    * @param [in] size The width and height to fit the loaded image to, 0.0 means whole image
52    * @param [in] fittingMode The method used to fit the shape of the image before loading to the shape defined by the size parameter.
53    * @param [in] samplingMode The filtering method used when sampling pixels from the input image while fitting it to desired size.
54    * @param [in] orientationCorrection Reorient the image to respect any orientation metadata in its header.
55    * @param [in] preMultiplyOnLoad ON if the image's color should be multiplied by it's alpha.
56    */
57   LoadingTask( uint32_t id,
58                const VisualUrl& url,
59                ImageDimensions dimensions,
60                FittingMode::Type fittingMode,
61                SamplingMode::Type samplingMode,
62                bool orientationCorrection,
63                DevelAsyncImageLoader::PreMultiplyOnLoad preMultiplyOnLoad);
64
65   /**
66    * Constructor.
67    * @param [in] id of the task
68    * @param [in] pixelBuffer of the to be masked image
69    * @param [in] maskPixelBuffer of the mask image
70    * @param [in] contentScale The factor to scale the content
71    * @param [in] cropToMask Whether to crop the content to the mask size
72    */
73   LoadingTask( uint32_t id,
74               Devel::PixelBuffer pixelBuffer,
75               Devel::PixelBuffer maskPixelBuffer,
76               float contentScale,
77               bool cropToMask );
78
79   /**
80    * Load the image
81    */
82   void Load();
83
84   /**
85    * Apply mask
86    */
87   void ApplyMask();
88
89 private:
90
91   // Undefined
92   LoadingTask( const LoadingTask& queue );
93
94   // Undefined
95   LoadingTask& operator=( const LoadingTask& queue );
96
97 public:
98
99   Devel::PixelBuffer pixelBuffer;   ///< pixelBuffer handle after successful load
100                                     ///< or pixelBuffer to be masked image in the mask task
101   VisualUrl          url;           ///< url of the image to load
102   uint32_t           id;            ///< The unique id associated with this task.
103   ImageDimensions    dimensions;    ///< dimensions to load
104   FittingMode::Type  fittingMode;   ///< fitting options
105   SamplingMode::Type samplingMode;  ///< sampling options
106   bool               orientationCorrection:1; ///< if orientation correction is needed
107   DevelAsyncImageLoader::PreMultiplyOnLoad            preMultiplyOnLoad; //< if the image's color should be multiplied by it's alpha
108
109   bool isMaskTask;                  ///< whether this task is for mask or not
110   Devel::PixelBuffer maskPixelBuffer; ///< pixelBuffer of mask image
111   float contentScale;               ///< The factor to scale the content
112   bool cropToMask;                  ///< Whether to crop the content to the mask size
113 };
114
115
116 /**
117  * The worker thread for image loading.
118  */
119 class ImageLoadThread : public Thread
120 {
121 public:
122
123   /**
124    * Constructor.
125    *
126    * @param[in] mTrigger The trigger to wake up the main thread.
127    */
128   ImageLoadThread( EventThreadCallback* mTrigger );
129
130   /**
131    * Destructor.
132    */
133   virtual ~ImageLoadThread();
134
135   /**
136    * Add a task in to the loading queue
137    *
138    * @param[in] task The task added to the queue.
139    *
140    * @note This class takes ownership of the task object
141    */
142   void AddTask( LoadingTask* task );
143
144   /**
145    * Pop the next task out from the completed queue.
146    *
147    * @return The next task to be processed.
148    */
149   LoadingTask* NextCompletedTask();
150
151   /**
152    * Remove the loading task from the waiting queue.
153    */
154   bool CancelTask( uint32_t loadingTaskId );
155
156   /**
157    * Remove all the loading tasks in the waiting queue.
158    */
159   void CancelAll();
160
161 private:
162
163   /**
164    * Pop the next loading task out from the queue to process.
165    *
166    * @return The next task to be processed.
167    */
168   LoadingTask* NextTaskToProcess();
169
170   /**
171    * Add a task in to the loading queue
172    *
173    * @param[in] task The task added to the queue.
174    */
175   void AddCompletedTask( LoadingTask* task );
176
177 protected:
178
179   /**
180    * The entry function of the worker thread.
181    * It fetches loading task from the loadQueue, loads the image and adds to the completeQueue.
182    */
183   virtual void Run();
184
185 private:
186
187   // Undefined
188   ImageLoadThread( const ImageLoadThread& thread );
189
190   // Undefined
191   ImageLoadThread& operator=( const ImageLoadThread& thread );
192
193 private:
194
195   Vector< LoadingTask* > mLoadQueue;     ///<The task queue with images for loading.
196   Vector< LoadingTask* > mCompleteQueue; ///<The task queue with images loaded.
197   EventThreadCallback*   mTrigger;
198   const Dali::LogFactoryInterface& mLogFactory; ///< The log factory
199
200   ConditionalWait        mConditionalWait;
201   Dali::Mutex            mMutex;
202 };
203
204 } // namespace Internal
205
206 } // namespace Toolkit
207
208 } // namespace Dali
209
210 #endif // DALI_TOOLKIT_IMAGE_LOAD_THREAD_H