Line data Source code
1 : /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* vim:set ts=2 sw=2 sts=2 et cindent: */
3 : /* This Source Code Form is subject to the terms of the Mozilla Public
4 : * License, v. 2.0. If a copy of the MPL was not distributed with this
5 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 :
7 : #include "ImageBitmapUtils.h"
8 : #include "ImageBitmapColorUtils.h"
9 : #include "ImageContainer.h"
10 : #include "libyuv.h"
11 : #include "mozilla/dom/ImageBitmapBinding.h"
12 : #include "mozilla/gfx/2D.h"
13 :
14 : #include <functional>
15 :
16 : using namespace libyuv;
17 : using namespace mozilla::gfx;
18 :
19 : namespace mozilla {
20 : namespace dom {
21 : namespace imagebitmapformat {
22 :
23 : class Utils;
24 : class Utils_RGBA32;
25 : class Utils_BGRA32;
26 : class Utils_RGB24;
27 : class Utils_BGR24;
28 : class Utils_Gray8;
29 : class Utils_YUV444P;
30 : class Utils_YUV422P;
31 : class Utils_YUV420P;
32 : class Utils_YUV420SP_NV12;
33 : class Utils_YUV420SP_NV21;
34 : class Utils_HSV;
35 : class Utils_Lab;
36 : class Utils_Depth;
37 :
38 0 : static int GetBytesPerPixelValue(ChannelPixelLayoutDataType aDataType)
39 : {
40 0 : switch (aDataType)
41 : {
42 : case ChannelPixelLayoutDataType::Uint8:
43 0 : return sizeof(uint8_t);
44 : case ChannelPixelLayoutDataType::Int8:
45 0 : return sizeof(int8_t);
46 : case ChannelPixelLayoutDataType::Uint16:
47 0 : return sizeof(uint16_t);
48 : case ChannelPixelLayoutDataType::Int16:
49 0 : return sizeof(int16_t);
50 : case ChannelPixelLayoutDataType::Uint32:
51 0 : return sizeof(uint32_t);
52 : case ChannelPixelLayoutDataType::Int32:
53 0 : return sizeof(int32_t);
54 : case ChannelPixelLayoutDataType::Float32:
55 0 : return sizeof(float);
56 : case ChannelPixelLayoutDataType::Float64:
57 0 : return sizeof(double);
58 : default:
59 0 : return 0;
60 : }
61 : }
62 :
63 : /*
64 : * The UtilsUniquePtr is a UniquePtr to ImageBitmapFormatUtils with a customized
65 : * deleter which does nothing. This is used as the return type of
66 : * ImageBitmapFormatUtils::GetUtils to prevent users deleting the returned
67 : * pointer.
68 : */
69 0 : struct DoNotDelete { void operator()(void* p) {} };
70 : using UtilsUniquePtr = UniquePtr<Utils, DoNotDelete>;
71 :
72 : /*
73 : * ImageBitmapFormatUtils is an abstract class which provides interfaces to
74 : * extract information of each ImageBitmapFormat and interfaces to convert
75 : * image data between different ImageBitmapFormats. For each kind of
76 : * ImageBitmapFromat, we derive a subclass from the ImageBitmapFormatUtils to
77 : * implement functionalities that are subject to the specific ImageBitmapFormat.
78 : *
79 : * ImageBitmapFormatUtils is an abstract class and its sub-classes are designed
80 : * as singletons. The singleton instance of sub-classes could be initialized and
81 : * accessed via the ImageBitmapFormatUtils::GetUtils() static method. The
82 : * singleton instance is a static local variable which does not need to be
83 : * released manually and, with the C++11 static initialization, the
84 : * initialization is thread-safe.
85 : *
86 : * ImageBitmapFormatUtils and its sub-classes are designed to unify operations
87 : * of ImageBitmap-extensions over different kinds of ImageBitmapFormats; they
88 : * provide following functionalities:
89 : *
90 : * (1) Create default/customized ImagePixelLayout object of each kind of
91 : * ImageBitmapFormat.
92 : * (2) Store the channel counts of each ImageBitmapFormat.
93 : * (3) Calculate the needed buffer size of each kind of ImageBitmapFormat with
94 : * given width, height and stride.
95 : * (4) Perform color conversion between supported ImageBitmapFormats. We use
96 : * _double dispatching_ to identify the source format and destination format
97 : * at run time. The _double dispatching_ here is mainly implemented by
98 : * overriding the _convertTo_ method over the ImageBitmapFormatUtils class
99 : * hierarchy and overloading the _convertFrom_ methods over all sub-classes
100 : * of ImageBitmapFormatUtils.
101 : */
102 : class Utils
103 : {
104 : public:
105 : // Get the singleton utility instance of the given ImageBitmapFormat.
106 : static UtilsUniquePtr GetUtils(ImageBitmapFormat aFormat);
107 :
108 : // Get the needed buffer size to store image data in the current
109 : // ImageBitmapFormat with the given width and height.
110 : // The current ImageBitmapFormat is the format used to implement the concrete
111 : // subclass of which the current instance is initialized.
112 : virtual uint32_t NeededBufferSize(uint32_t width, uint32_t height) = 0;
113 :
114 : // Creates a default ImagePixelLayout object of the current ImageBitmapFormat
115 : // with the given width, height and stride.
116 : virtual UniquePtr<ImagePixelLayout>
117 : CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride) = 0;
118 :
119 : // Convert the source image data (stored in the aSrcBuffer and described by
120 : // the aSrcLayout) from the current ImageBitmapFormat to the given
121 : // ImageBitmapFormat, aDstFormat.
122 : // The converted image data is stored in the aDstBuffer and described by the
123 : // returned ImagePixelLayout object.
124 : virtual UniquePtr<ImagePixelLayout>
125 : ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
126 :
127 : // ConvertFrom():
128 : // Convert the source image data (which is in the aSrcFormat format, the pixel
129 : // layout is described by the aSrcLayout and the raw data is stored in the
130 : // aSrcBuffer) to the current ImageBitmapFormat.
131 : // The converted image data is stored in the aDstBuffer and described by the
132 : // returned ImagePixelLayout object.
133 : virtual UniquePtr<ImagePixelLayout>
134 : ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
135 :
136 : virtual UniquePtr<ImagePixelLayout>
137 : ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
138 :
139 : virtual UniquePtr<ImagePixelLayout>
140 : ConvertFrom(Utils_RGB24* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
141 :
142 : virtual UniquePtr<ImagePixelLayout>
143 : ConvertFrom(Utils_BGR24* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
144 :
145 : virtual UniquePtr<ImagePixelLayout>
146 : ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
147 :
148 : virtual UniquePtr<ImagePixelLayout>
149 : ConvertFrom(Utils_YUV444P* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
150 :
151 : virtual UniquePtr<ImagePixelLayout>
152 : ConvertFrom(Utils_YUV422P* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
153 :
154 : virtual UniquePtr<ImagePixelLayout>
155 : ConvertFrom(Utils_YUV420P* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
156 :
157 : virtual UniquePtr<ImagePixelLayout>
158 : ConvertFrom(Utils_YUV420SP_NV12* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
159 :
160 : virtual UniquePtr<ImagePixelLayout>
161 : ConvertFrom(Utils_YUV420SP_NV21* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
162 :
163 : virtual UniquePtr<ImagePixelLayout>
164 : ConvertFrom(Utils_HSV* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
165 :
166 : virtual UniquePtr<ImagePixelLayout>
167 : ConvertFrom(Utils_Lab* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
168 :
169 : virtual UniquePtr<ImagePixelLayout>
170 : ConvertFrom(Utils_Depth* aSrcFormat, const uint8_t* aSrcBuffer, const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer) = 0;
171 :
172 : // Check whether or not the current ImageBitmapFormat can be converted from
173 : // the given ImageBitmapFormat.
174 : virtual bool
175 : CanConvertFrom(ImageBitmapFormat aSrcFormat) = 0;
176 :
177 : // Get the number of channels.
178 0 : uint8_t GetChannelCount() const
179 : {
180 0 : return mChannels;
181 : }
182 :
183 : protected:
184 0 : Utils(uint32_t aChannels,
185 : ChannelPixelLayoutDataType aDataType)
186 0 : : mChannels(aChannels)
187 0 : , mBytesPerPixelValue(GetBytesPerPixelValue(aDataType))
188 0 : , mDataType(aDataType)
189 : {
190 0 : }
191 :
192 0 : virtual ~Utils()
193 0 : {
194 0 : }
195 :
196 : const uint8_t mChannels;
197 : const int mBytesPerPixelValue;
198 : const ChannelPixelLayoutDataType mDataType;
199 : };
200 :
201 : #define DECLARE_Utils(NAME) \
202 : class Utils_ ## NAME : public Utils \
203 : { \
204 : private: \
205 : explicit Utils_ ## NAME (); \
206 : ~Utils_ ## NAME () = default; \
207 : Utils_ ## NAME (Utils_ ## NAME const &) = delete; \
208 : Utils_ ## NAME (Utils_ ## NAME &&) = delete; \
209 : Utils_ ## NAME & operator=(Utils_ ## NAME const &) = delete; \
210 : Utils_ ## NAME & operator=(Utils_ ## NAME &&) = delete; \
211 : \
212 : public: \
213 : static Utils_ ## NAME & GetInstance(); \
214 : \
215 : virtual uint32_t NeededBufferSize(uint32_t aWidth, uint32_t aHeight) override; \
216 : \
217 : virtual UniquePtr<ImagePixelLayout> \
218 : CreateDefaultLayout(uint32_t, uint32_t, uint32_t) override; \
219 : \
220 : virtual UniquePtr<ImagePixelLayout> \
221 : ConvertTo(Utils*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
222 : \
223 : virtual UniquePtr<ImagePixelLayout> \
224 : ConvertFrom(Utils_RGBA32*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
225 : \
226 : virtual UniquePtr<ImagePixelLayout> \
227 : ConvertFrom(Utils_BGRA32*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
228 : \
229 : virtual UniquePtr<ImagePixelLayout> \
230 : ConvertFrom(Utils_RGB24*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
231 : \
232 : virtual UniquePtr<ImagePixelLayout> \
233 : ConvertFrom(Utils_BGR24*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
234 : \
235 : virtual UniquePtr<ImagePixelLayout> \
236 : ConvertFrom(Utils_Gray8*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
237 : \
238 : virtual UniquePtr<ImagePixelLayout> \
239 : ConvertFrom(Utils_YUV444P*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
240 : \
241 : virtual UniquePtr<ImagePixelLayout> \
242 : ConvertFrom(Utils_YUV422P*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
243 : \
244 : virtual UniquePtr<ImagePixelLayout> \
245 : ConvertFrom(Utils_YUV420P*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
246 : \
247 : virtual UniquePtr<ImagePixelLayout> \
248 : ConvertFrom(Utils_YUV420SP_NV12*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
249 : \
250 : virtual UniquePtr<ImagePixelLayout> \
251 : ConvertFrom(Utils_YUV420SP_NV21*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
252 : \
253 : virtual UniquePtr<ImagePixelLayout> \
254 : ConvertFrom(Utils_HSV*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
255 : \
256 : virtual UniquePtr<ImagePixelLayout> \
257 : ConvertFrom(Utils_Lab*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
258 : \
259 : virtual UniquePtr<ImagePixelLayout> \
260 : ConvertFrom(Utils_Depth*, const uint8_t*, const ImagePixelLayout*, uint8_t*) override; \
261 : \
262 : virtual bool \
263 : CanConvertFrom(ImageBitmapFormat) override; \
264 : };
265 :
266 0 : DECLARE_Utils(RGBA32)
267 0 : DECLARE_Utils(BGRA32)
268 0 : DECLARE_Utils(RGB24)
269 0 : DECLARE_Utils(BGR24)
270 0 : DECLARE_Utils(Gray8)
271 0 : DECLARE_Utils(YUV444P)
272 0 : DECLARE_Utils(YUV422P)
273 0 : DECLARE_Utils(YUV420P)
274 0 : DECLARE_Utils(YUV420SP_NV12)
275 0 : DECLARE_Utils(YUV420SP_NV21)
276 0 : DECLARE_Utils(HSV)
277 0 : DECLARE_Utils(Lab)
278 0 : DECLARE_Utils(Depth)
279 :
280 : #undef DECLARE_Utils
281 :
282 : /*
283 : * ImageBitmapFormatUtils.
284 : */
285 : /* static */ UtilsUniquePtr
286 0 : Utils::GetUtils(ImageBitmapFormat aFormat)
287 : {
288 0 : switch(aFormat)
289 : {
290 : case ImageBitmapFormat::RGBA32:
291 0 : return UtilsUniquePtr(&Utils_RGBA32::GetInstance());
292 : case ImageBitmapFormat::BGRA32:
293 0 : return UtilsUniquePtr(&Utils_BGRA32::GetInstance());
294 : case ImageBitmapFormat::RGB24:
295 0 : return UtilsUniquePtr(&Utils_RGB24::GetInstance());
296 : case ImageBitmapFormat::BGR24:
297 0 : return UtilsUniquePtr(&Utils_BGR24::GetInstance());
298 : case ImageBitmapFormat::GRAY8:
299 0 : return UtilsUniquePtr(&Utils_Gray8::GetInstance());
300 : case ImageBitmapFormat::YUV444P:
301 0 : return UtilsUniquePtr(&Utils_YUV444P::GetInstance());
302 : case ImageBitmapFormat::YUV422P:
303 0 : return UtilsUniquePtr(&Utils_YUV422P::GetInstance());
304 : case ImageBitmapFormat::YUV420P:
305 0 : return UtilsUniquePtr(&Utils_YUV420P::GetInstance());
306 : case ImageBitmapFormat::YUV420SP_NV12:
307 0 : return UtilsUniquePtr(&Utils_YUV420SP_NV12::GetInstance());
308 : case ImageBitmapFormat::YUV420SP_NV21:
309 0 : return UtilsUniquePtr(&Utils_YUV420SP_NV21::GetInstance());
310 : case ImageBitmapFormat::HSV:
311 0 : return UtilsUniquePtr(&Utils_HSV::GetInstance());
312 : case ImageBitmapFormat::Lab:
313 0 : return UtilsUniquePtr(&Utils_Lab::GetInstance());
314 : case ImageBitmapFormat::DEPTH:
315 0 : return UtilsUniquePtr(&Utils_Depth::GetInstance());
316 : default:
317 0 : return nullptr;
318 : }
319 : }
320 :
321 : /*
322 : * Helper functions.
323 : */
324 : template<typename SrcType, typename DstType>
325 : static UniquePtr<ImagePixelLayout>
326 0 : CvtSimpleImgToSimpleImg(Utils* aSrcUtils, const SrcType* aSrcBuffer,
327 : const ImagePixelLayout* aSrcLayout, DstType* aDstBuffer,
328 : ImageBitmapFormat aDstFormat, int aDstChannelCount,
329 : const std::function<int (const SrcType*, int, DstType*, int, int, int)>& converter)
330 : {
331 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
332 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
333 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
334 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
335 :
336 0 : const nsTArray<ChannelPixelLayout>& channels = *aSrcLayout;
337 0 : MOZ_ASSERT(channels.Length() == aSrcUtils->GetChannelCount(),
338 : "The channel count is wrong.");
339 :
340 0 : const int dstStride = channels[0].mWidth * aDstChannelCount * sizeof(DstType);
341 0 : int rv = converter(aSrcBuffer, channels[0].mStride,
342 : aDstBuffer, dstStride,
343 0 : channels[0].mWidth, channels[0].mHeight);
344 :
345 0 : if (NS_WARN_IF(rv != 0)) {
346 0 : return nullptr;
347 : }
348 :
349 0 : return CreateDefaultPixelLayout(aDstFormat, channels[0].mWidth,
350 0 : channels[0].mHeight, dstStride);
351 : }
352 :
353 : static UniquePtr<ImagePixelLayout>
354 0 : CvtYUVImgToSimpleImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
355 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
356 : ImageBitmapFormat aDstFormat, int aDstChannelCount,
357 : const std::function<int (const uint8_t*, int, const uint8_t*, int, const uint8_t*, int, uint8_t*, int, int, int)>& converter)
358 : {
359 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
360 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
361 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
362 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
363 :
364 0 : const nsTArray<ChannelPixelLayout>& channels = *aSrcLayout;
365 0 : MOZ_ASSERT(channels.Length() == aSrcUtils->GetChannelCount(),
366 : "The channel count is wrong.");
367 :
368 0 : const int dstStride = channels[0].mWidth * aDstChannelCount * sizeof(uint8_t);
369 0 : int rv = converter(aSrcBuffer + channels[0].mOffset, channels[0].mStride,
370 0 : aSrcBuffer + channels[1].mOffset, channels[1].mStride,
371 0 : aSrcBuffer + channels[2].mOffset, channels[2].mStride,
372 : aDstBuffer, dstStride,
373 0 : channels[0].mWidth, channels[0].mHeight);
374 :
375 0 : if (NS_WARN_IF(rv != 0)) {
376 0 : return nullptr;
377 : }
378 :
379 0 : return CreateDefaultPixelLayout(aDstFormat, channels[0].mWidth,
380 0 : channels[0].mHeight, dstStride);
381 : }
382 :
383 : static UniquePtr<ImagePixelLayout>
384 0 : CvtNVImgToSimpleImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
385 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
386 : ImageBitmapFormat aDstFormat, int aDstChannelCount,
387 : const std::function<int (const uint8_t*, int, const uint8_t*, int, uint8_t*, int, int, int)>& converter)
388 : {
389 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
390 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
391 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
392 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
393 :
394 0 : const nsTArray<ChannelPixelLayout>& channels = *aSrcLayout;
395 0 : MOZ_ASSERT(channels.Length() == aSrcUtils->GetChannelCount(),
396 : "The channel count is wrong.");
397 :
398 0 : const int dstStride = channels[0].mWidth * aDstChannelCount * sizeof(uint8_t);
399 0 : int rv = converter(aSrcBuffer + channels[0].mOffset, channels[0].mStride,
400 0 : aSrcBuffer + channels[1].mOffset, channels[1].mStride,
401 : aDstBuffer, dstStride,
402 0 : channels[0].mWidth, channels[0].mHeight);
403 :
404 0 : if (NS_WARN_IF(rv != 0)) {
405 0 : return nullptr;
406 : }
407 :
408 0 : return CreateDefaultPixelLayout(aDstFormat, channels[0].mWidth,
409 0 : channels[0].mHeight, dstStride);
410 : }
411 :
412 : static UniquePtr<ImagePixelLayout>
413 0 : CvtSimpleImgToYUVImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
414 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
415 : ImageBitmapFormat aDstFormat,
416 : const std::function<int (const uint8_t*, int, uint8_t*, int, uint8_t*, int, uint8_t*, int, int, int)>& converter)
417 : {
418 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
419 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
420 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
421 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
422 :
423 : UniquePtr<ImagePixelLayout> layout =
424 0 : CreateDefaultPixelLayout(aDstFormat, (*aSrcLayout)[0].mWidth,
425 0 : (*aSrcLayout)[0].mHeight, (*aSrcLayout)[0].mWidth);
426 :
427 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout.");
428 :
429 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
430 :
431 0 : int rv = converter(aSrcBuffer, (*aSrcLayout)[0].mStride,
432 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
433 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
434 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
435 0 : channels[0].mWidth, channels[0].mHeight);
436 :
437 0 : if (NS_WARN_IF(rv != 0)) {
438 0 : return nullptr;
439 : }
440 :
441 0 : return layout;
442 : }
443 :
444 : static UniquePtr<ImagePixelLayout>
445 0 : CvtSimpleImgToNVImg(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
446 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
447 : ImageBitmapFormat aDstFormat,
448 : const std::function<int (const uint8_t*, int, uint8_t*, int, uint8_t*, int, int, int)>& converter)
449 : {
450 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
451 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
452 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
453 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
454 :
455 : UniquePtr<ImagePixelLayout> layout =
456 0 : CreateDefaultPixelLayout(aDstFormat, (*aSrcLayout)[0].mWidth,
457 0 : (*aSrcLayout)[0].mHeight, (*aSrcLayout)[0].mWidth);
458 :
459 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout.");
460 :
461 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
462 :
463 0 : int rv = converter(aSrcBuffer, (*aSrcLayout)[0].mStride,
464 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
465 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
466 0 : channels[0].mWidth, channels[0].mHeight);
467 :
468 0 : if (NS_WARN_IF(rv != 0)) {
469 0 : return nullptr;
470 : }
471 :
472 0 : return layout;
473 : }
474 :
475 : template<class SrcUtilsType, class DstUtilsType>
476 : static UniquePtr<ImagePixelLayout>
477 0 : TwoPassConversion(SrcUtilsType* aSrcUtils, const uint8_t* aSrcBuffer,
478 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
479 : ImageBitmapFormat aMiddleFormat, DstUtilsType* aDstUtils)
480 : {
481 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null source utility.");
482 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
483 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
484 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
485 :
486 : // I444 -> I420 -> I422
487 0 : UtilsUniquePtr yuv420PUtils = Utils::GetUtils(aMiddleFormat);
488 0 : UniquePtr<uint8_t> yuv420PBuffer(new uint8_t[yuv420PUtils->NeededBufferSize((*aSrcLayout)[0].mWidth, (*aSrcLayout)[0].mHeight)]);
489 0 : UniquePtr<ImagePixelLayout> yuv420PLayout = yuv420PUtils->ConvertFrom(aSrcUtils, aSrcBuffer, aSrcLayout, yuv420PBuffer.get());
490 0 : return yuv420PUtils->ConvertTo(aDstUtils, yuv420PBuffer.get(), yuv420PLayout.get(), aDstBuffer);
491 : }
492 :
493 : static UniquePtr<ImagePixelLayout>
494 0 : PureCopy(Utils* aSrcUtils, const uint8_t* aSrcBuffer,
495 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer,
496 : ImageBitmapFormat aDstFormat)
497 : {
498 0 : MOZ_ASSERT(aSrcUtils, "Convert color from a null utility object.");
499 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
500 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
501 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
502 :
503 0 : const nsTArray<ChannelPixelLayout>& channels = *aSrcLayout;
504 0 : MOZ_ASSERT(channels.Length() == aSrcUtils->GetChannelCount(),
505 : "The channel count is wrong.");
506 :
507 :
508 0 : uint32_t length = 0;
509 :
510 0 : if (aDstFormat == ImageBitmapFormat::RGBA32 ||
511 0 : aDstFormat == ImageBitmapFormat::BGRA32 ||
512 0 : aDstFormat == ImageBitmapFormat::RGB24 ||
513 0 : aDstFormat == ImageBitmapFormat::BGR24 ||
514 0 : aDstFormat == ImageBitmapFormat::GRAY8 ||
515 0 : aDstFormat == ImageBitmapFormat::HSV ||
516 0 : aDstFormat == ImageBitmapFormat::Lab ||
517 : aDstFormat == ImageBitmapFormat::DEPTH) {
518 0 : length = channels[0].mHeight * channels[0].mStride;
519 0 : } else if (aDstFormat == ImageBitmapFormat::YUV444P ||
520 0 : aDstFormat == ImageBitmapFormat::YUV422P ||
521 : aDstFormat == ImageBitmapFormat::YUV420P) {
522 0 : length = channels[0].mHeight * channels[0].mStride +
523 0 : channels[1].mHeight * channels[1].mStride +
524 0 : channels[2].mHeight * channels[2].mStride;
525 0 : } else if (aDstFormat == ImageBitmapFormat::YUV420SP_NV12 ||
526 : aDstFormat == ImageBitmapFormat::YUV420SP_NV21) {
527 0 : length = channels[0].mHeight * channels[0].mStride +
528 0 : channels[1].mHeight * channels[1].mStride;
529 : }
530 :
531 0 : memcpy(aDstBuffer, aSrcBuffer, length);
532 :
533 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(*aSrcLayout));
534 0 : return layout;
535 : }
536 :
537 : UniquePtr<ImagePixelLayout>
538 0 : CreateDefaultLayoutForSimpleImage(uint32_t aWidth, uint32_t aHeight,
539 : uint32_t aStride, int aChannels,
540 : int aBytesPerPixelValue,
541 : ChannelPixelLayoutDataType aDataType)
542 : {
543 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(aChannels));
544 :
545 : // set mChannels
546 0 : for (uint8_t i = 0; i < aChannels; ++i) {
547 0 : ChannelPixelLayout* channel = layout->AppendElement();
548 0 : channel->mOffset = i * aBytesPerPixelValue;
549 0 : channel->mWidth = aWidth;
550 0 : channel->mHeight = aHeight;
551 0 : channel->mDataType = aDataType; //ChannelPixelLayoutDataType::Uint8;
552 0 : channel->mStride = aStride;
553 0 : channel->mSkip = aChannels - 1;
554 : }
555 :
556 0 : return layout;
557 : }
558 :
559 : /*
560 : * Utils_RGBA32.
561 : */
562 : /* static */Utils_RGBA32&
563 0 : Utils_RGBA32::GetInstance()
564 : {
565 0 : static Utils_RGBA32 instance;
566 0 : return instance;
567 : }
568 :
569 0 : Utils_RGBA32::Utils_RGBA32()
570 0 : : Utils(4, ChannelPixelLayoutDataType::Uint8)
571 : {
572 0 : }
573 :
574 : uint32_t
575 0 : Utils_RGBA32::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
576 : {
577 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
578 : }
579 :
580 : UniquePtr<ImagePixelLayout>
581 0 : Utils_RGBA32::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
582 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
583 : {
584 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
585 : }
586 :
587 : UniquePtr<ImagePixelLayout>
588 0 : Utils_RGBA32::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
589 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
590 : {
591 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32);
592 : }
593 :
594 : UniquePtr<ImagePixelLayout>
595 0 : Utils_RGBA32::ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer,
596 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
597 : {
598 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &libyuv::ABGRToARGB);
599 : }
600 :
601 : UniquePtr<ImagePixelLayout>
602 0 : Utils_RGBA32::ConvertFrom(Utils_RGB24* aSrcFormat, const uint8_t* aSrcBuffer,
603 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
604 : {
605 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &RGB24ToRGBA32);
606 : }
607 :
608 : UniquePtr<ImagePixelLayout>
609 0 : Utils_RGBA32::ConvertFrom(Utils_BGR24* aSrcFormat, const uint8_t* aSrcBuffer,
610 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
611 : {
612 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &BGR24ToRGBA32);
613 : }
614 :
615 : UniquePtr<ImagePixelLayout>
616 0 : Utils_RGBA32::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
617 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
618 : {
619 0 : return nullptr;
620 : }
621 :
622 : UniquePtr<ImagePixelLayout>
623 0 : Utils_RGBA32::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
624 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
625 : {
626 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &YUV444PToRGBA32);
627 : }
628 :
629 : UniquePtr<ImagePixelLayout>
630 0 : Utils_RGBA32::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
631 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
632 : {
633 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &YUV422PToRGBA32);
634 : }
635 :
636 : UniquePtr<ImagePixelLayout>
637 0 : Utils_RGBA32::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
638 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
639 : {
640 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &libyuv::I420ToABGR);
641 : }
642 :
643 : UniquePtr<ImagePixelLayout>
644 0 : Utils_RGBA32::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
645 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
646 : {
647 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &NV12ToRGBA32);
648 : }
649 :
650 : UniquePtr<ImagePixelLayout>
651 0 : Utils_RGBA32::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
652 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
653 : {
654 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &NV21ToRGBA32);
655 : }
656 :
657 : UniquePtr<ImagePixelLayout>
658 0 : Utils_RGBA32::ConvertFrom(Utils_HSV* aSrcFormat, const uint8_t* aSrcBuffer,
659 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
660 : {
661 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &HSVToRGBA32);
662 : }
663 :
664 : UniquePtr<ImagePixelLayout>
665 0 : Utils_RGBA32::ConvertFrom(Utils_Lab* aSrcFormat, const uint8_t* aSrcBuffer,
666 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
667 : {
668 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGBA32, 4, &LabToRGBA32);
669 : }
670 :
671 : UniquePtr<ImagePixelLayout>
672 0 : Utils_RGBA32::ConvertFrom(Utils_Depth* aSrcFormat, const uint8_t* aSrcBuffer,
673 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
674 : {
675 0 : return nullptr;
676 : }
677 :
678 : bool
679 0 : Utils_RGBA32::CanConvertFrom(ImageBitmapFormat aSrcFormat)
680 : {
681 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
682 : aSrcFormat == ImageBitmapFormat::DEPTH) {
683 0 : return false;
684 : }
685 :
686 0 : return true;
687 : }
688 :
689 : UniquePtr<ImagePixelLayout>
690 0 : Utils_RGBA32::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
691 : {
692 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
693 : }
694 :
695 : /*
696 : * Utils_BGRA32.
697 : */
698 : /* static */Utils_BGRA32&
699 0 : Utils_BGRA32::GetInstance()
700 : {
701 0 : static Utils_BGRA32 instance;
702 0 : return instance;
703 : }
704 :
705 0 : Utils_BGRA32::Utils_BGRA32()
706 0 : : Utils(4, ChannelPixelLayoutDataType::Uint8)
707 : {
708 0 : }
709 :
710 : uint32_t
711 0 : Utils_BGRA32::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
712 : {
713 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
714 : }
715 :
716 : UniquePtr<ImagePixelLayout>
717 0 : Utils_BGRA32::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
718 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
719 : {
720 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
721 : }
722 :
723 : UniquePtr<ImagePixelLayout>
724 0 : Utils_BGRA32::ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer,
725 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
726 : {
727 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &libyuv::ABGRToARGB);
728 : }
729 :
730 : UniquePtr<ImagePixelLayout>
731 0 : Utils_BGRA32::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
732 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
733 : {
734 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32);
735 : }
736 :
737 : UniquePtr<ImagePixelLayout>
738 0 : Utils_BGRA32::ConvertFrom(Utils_RGB24* aSrcFormat, const uint8_t* aSrcBuffer,
739 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
740 : {
741 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &RGB24ToBGRA32);
742 : }
743 :
744 : UniquePtr<ImagePixelLayout>
745 0 : Utils_BGRA32::ConvertFrom(Utils_BGR24* aSrcFormat, const uint8_t* aSrcBuffer,
746 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
747 : {
748 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &BGR24ToBGRA32);
749 : }
750 :
751 : UniquePtr<ImagePixelLayout>
752 0 : Utils_BGRA32::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
753 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
754 : {
755 0 : return nullptr;
756 : }
757 :
758 : UniquePtr<ImagePixelLayout>
759 0 : Utils_BGRA32::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
760 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
761 : {
762 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &YUV444PToBGRA32);
763 : }
764 :
765 : UniquePtr<ImagePixelLayout>
766 0 : Utils_BGRA32::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
767 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
768 : {
769 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &libyuv::I422ToARGB);
770 : }
771 :
772 : UniquePtr<ImagePixelLayout>
773 0 : Utils_BGRA32::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
774 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
775 : {
776 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &libyuv::I420ToARGB);
777 : }
778 :
779 : UniquePtr<ImagePixelLayout>
780 0 : Utils_BGRA32::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
781 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
782 : {
783 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &libyuv::NV12ToARGB);
784 : }
785 :
786 : UniquePtr<ImagePixelLayout>
787 0 : Utils_BGRA32::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
788 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
789 : {
790 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &libyuv::NV21ToARGB);
791 : }
792 :
793 : UniquePtr<ImagePixelLayout>
794 0 : Utils_BGRA32::ConvertFrom(Utils_HSV* aSrcFormat, const uint8_t* aSrcBuffer,
795 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
796 : {
797 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &HSVToBGRA32);
798 : }
799 :
800 : UniquePtr<ImagePixelLayout>
801 0 : Utils_BGRA32::ConvertFrom(Utils_Lab* aSrcFormat, const uint8_t* aSrcBuffer,
802 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
803 : {
804 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGRA32, 4, &LabToBGRA32);
805 : }
806 :
807 : UniquePtr<ImagePixelLayout>
808 0 : Utils_BGRA32::ConvertFrom(Utils_Depth* aSrcFormat, const uint8_t* aSrcBuffer,
809 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
810 : {
811 0 : return nullptr;
812 : }
813 :
814 : bool
815 0 : Utils_BGRA32::CanConvertFrom(ImageBitmapFormat aSrcFormat)
816 : {
817 0 : if (aSrcFormat == ImageBitmapFormat::RGBA32 ||
818 0 : aSrcFormat == ImageBitmapFormat::BGRA32 ||
819 : aSrcFormat == ImageBitmapFormat::YUV420P) {
820 0 : return true;
821 : }
822 :
823 0 : return false;
824 : }
825 :
826 : UniquePtr<ImagePixelLayout>
827 0 : Utils_BGRA32::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
828 : {
829 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
830 : }
831 :
832 : /*
833 : * Utils_RGB24.
834 : */
835 : /* static */Utils_RGB24&
836 0 : Utils_RGB24::GetInstance()
837 : {
838 0 : static Utils_RGB24 instance;
839 0 : return instance;
840 : }
841 :
842 0 : Utils_RGB24::Utils_RGB24()
843 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
844 : {
845 0 : }
846 :
847 : uint32_t
848 0 : Utils_RGB24::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
849 : {
850 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
851 : }
852 :
853 : UniquePtr<ImagePixelLayout>
854 0 : Utils_RGB24::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
855 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
856 : {
857 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
858 : }
859 :
860 : UniquePtr<ImagePixelLayout>
861 0 : Utils_RGB24::ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer,
862 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
863 : {
864 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &RGBA32ToRGB24);
865 : }
866 :
867 : UniquePtr<ImagePixelLayout>
868 0 : Utils_RGB24::ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer,
869 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
870 : {
871 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &BGRA32ToRGB24);
872 : }
873 :
874 : UniquePtr<ImagePixelLayout>
875 0 : Utils_RGB24::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
876 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
877 : {
878 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24);
879 : }
880 :
881 : UniquePtr<ImagePixelLayout>
882 0 : Utils_RGB24::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
883 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
884 : {
885 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &BGR24ToRGB24);
886 : }
887 :
888 : UniquePtr<ImagePixelLayout>
889 0 : Utils_RGB24::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
890 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
891 : {
892 0 : return nullptr;
893 : }
894 :
895 : UniquePtr<ImagePixelLayout>
896 0 : Utils_RGB24::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
897 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
898 : {
899 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &YUV444PToRGB24);
900 : }
901 :
902 : UniquePtr<ImagePixelLayout>
903 0 : Utils_RGB24::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
904 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
905 : {
906 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &YUV422PToRGB24);
907 : }
908 :
909 : UniquePtr<ImagePixelLayout>
910 0 : Utils_RGB24::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
911 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
912 : {
913 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &YUV420PToRGB24);
914 : }
915 :
916 : UniquePtr<ImagePixelLayout>
917 0 : Utils_RGB24::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
918 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
919 : {
920 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &NV12ToRGB24);
921 : }
922 :
923 : UniquePtr<ImagePixelLayout>
924 0 : Utils_RGB24::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
925 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
926 : {
927 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &NV21ToRGB24);
928 : }
929 :
930 : UniquePtr<ImagePixelLayout>
931 0 : Utils_RGB24::ConvertFrom(Utils_HSV* aSrcFormat, const uint8_t* aSrcBuffer,
932 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
933 : {
934 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &HSVToRGB24);
935 : }
936 :
937 : UniquePtr<ImagePixelLayout>
938 0 : Utils_RGB24::ConvertFrom(Utils_Lab* aSrcFormat, const uint8_t* aSrcBuffer,
939 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
940 : {
941 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, 3, &LabToRGB24);
942 : }
943 :
944 : UniquePtr<ImagePixelLayout>
945 0 : Utils_RGB24::ConvertFrom(Utils_Depth* aSrcFormat, const uint8_t* aSrcBuffer,
946 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
947 : {
948 0 : return nullptr;
949 : }
950 :
951 : bool
952 0 : Utils_RGB24::CanConvertFrom(ImageBitmapFormat aSrcFormat)
953 : {
954 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
955 : aSrcFormat == ImageBitmapFormat::DEPTH) {
956 0 : return false;
957 : }
958 :
959 0 : return true;
960 : }
961 :
962 : UniquePtr<ImagePixelLayout>
963 0 : Utils_RGB24::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
964 : {
965 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
966 : }
967 :
968 : /*
969 : * Utils_BGR24.
970 : */
971 : /* static */Utils_BGR24&
972 0 : Utils_BGR24::GetInstance()
973 : {
974 0 : static Utils_BGR24 instance;
975 0 : return instance;
976 : }
977 :
978 0 : Utils_BGR24::Utils_BGR24()
979 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
980 : {
981 0 : }
982 :
983 : uint32_t
984 0 : Utils_BGR24::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
985 : {
986 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
987 : }
988 :
989 : UniquePtr<ImagePixelLayout>
990 0 : Utils_BGR24::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
991 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
992 : {
993 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
994 : }
995 :
996 : UniquePtr<ImagePixelLayout>
997 0 : Utils_BGR24::ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer,
998 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
999 : {
1000 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &RGBA32ToBGR24);
1001 : }
1002 :
1003 : UniquePtr<ImagePixelLayout>
1004 0 : Utils_BGR24::ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer,
1005 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1006 : {
1007 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &BGRA32ToBGR24);
1008 : }
1009 :
1010 : UniquePtr<ImagePixelLayout>
1011 0 : Utils_BGR24::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
1012 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1013 : {
1014 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &RGB24ToBGR24);
1015 : }
1016 :
1017 : UniquePtr<ImagePixelLayout>
1018 0 : Utils_BGR24::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
1019 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1020 : {
1021 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24);
1022 : }
1023 :
1024 : UniquePtr<ImagePixelLayout>
1025 0 : Utils_BGR24::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
1026 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1027 : {
1028 0 : return nullptr;
1029 : }
1030 :
1031 : UniquePtr<ImagePixelLayout>
1032 0 : Utils_BGR24::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
1033 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1034 : {
1035 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &YUV444PToBGR24);
1036 : }
1037 :
1038 : UniquePtr<ImagePixelLayout>
1039 0 : Utils_BGR24::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
1040 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1041 : {
1042 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &YUV422PToBGR24);
1043 : }
1044 :
1045 : UniquePtr<ImagePixelLayout>
1046 0 : Utils_BGR24::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
1047 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1048 : {
1049 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &YUV420PToBGR24);
1050 : }
1051 :
1052 : UniquePtr<ImagePixelLayout>
1053 0 : Utils_BGR24::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
1054 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1055 : {
1056 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &NV12ToBGR24);
1057 : }
1058 :
1059 : UniquePtr<ImagePixelLayout>
1060 0 : Utils_BGR24::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
1061 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1062 : {
1063 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &NV21ToBGR24);
1064 : }
1065 :
1066 : UniquePtr<ImagePixelLayout>
1067 0 : Utils_BGR24::ConvertFrom(Utils_HSV* aSrcFormat, const uint8_t* aSrcBuffer,
1068 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1069 : {
1070 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &HSVToBGR24);
1071 : }
1072 :
1073 : UniquePtr<ImagePixelLayout>
1074 0 : Utils_BGR24::ConvertFrom(Utils_Lab* aSrcFormat, const uint8_t* aSrcBuffer,
1075 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1076 : {
1077 0 : return CvtSimpleImgToSimpleImg<float, uint8_t>(aSrcFormat, (const float*)aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::BGR24, 3, &LabToBGR24);
1078 : }
1079 :
1080 : UniquePtr<ImagePixelLayout>
1081 0 : Utils_BGR24::ConvertFrom(Utils_Depth* aSrcFormat, const uint8_t* aSrcBuffer,
1082 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1083 : {
1084 0 : return nullptr;
1085 : }
1086 :
1087 : bool
1088 0 : Utils_BGR24::CanConvertFrom(ImageBitmapFormat aSrcFormat)
1089 : {
1090 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
1091 : aSrcFormat == ImageBitmapFormat::DEPTH) {
1092 0 : return false;
1093 : }
1094 :
1095 0 : return true;
1096 : }
1097 :
1098 : UniquePtr<ImagePixelLayout>
1099 0 : Utils_BGR24::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
1100 : {
1101 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
1102 : }
1103 :
1104 : /*
1105 : * Utils_Gray8.
1106 : */
1107 : /* static */Utils_Gray8&
1108 0 : Utils_Gray8::GetInstance()
1109 : {
1110 0 : static Utils_Gray8 instance;
1111 0 : return instance;
1112 : }
1113 :
1114 0 : Utils_Gray8::Utils_Gray8()
1115 0 : : Utils(1, ChannelPixelLayoutDataType::Uint8)
1116 : {
1117 0 : }
1118 :
1119 : uint32_t
1120 0 : Utils_Gray8::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
1121 : {
1122 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
1123 : }
1124 :
1125 : UniquePtr<ImagePixelLayout>
1126 0 : Utils_Gray8::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
1127 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1128 : {
1129 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
1130 : }
1131 :
1132 : UniquePtr<ImagePixelLayout>
1133 0 : Utils_Gray8::ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer,
1134 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1135 : {
1136 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &RGBA32ToGray8);
1137 : }
1138 :
1139 : UniquePtr<ImagePixelLayout>
1140 0 : Utils_Gray8::ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer,
1141 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1142 : {
1143 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcFormat, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &BGRA32ToGray8);
1144 : }
1145 :
1146 : UniquePtr<ImagePixelLayout>
1147 0 : Utils_Gray8::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
1148 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1149 : {
1150 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &RGB24ToGray8);
1151 : }
1152 :
1153 : UniquePtr<ImagePixelLayout>
1154 0 : Utils_Gray8::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
1155 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1156 : {
1157 0 : return CvtSimpleImgToSimpleImg<uint8_t, uint8_t>(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &BGR24ToGray8);
1158 : }
1159 :
1160 : UniquePtr<ImagePixelLayout>
1161 0 : Utils_Gray8::ConvertFrom(Utils_Gray8* aSrcUtils, const uint8_t* aSrcBuffer,
1162 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1163 : {
1164 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8);
1165 : }
1166 :
1167 : UniquePtr<ImagePixelLayout>
1168 0 : Utils_Gray8::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
1169 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1170 : {
1171 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &YUV444PToGray8);
1172 : }
1173 :
1174 : UniquePtr<ImagePixelLayout>
1175 0 : Utils_Gray8::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
1176 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1177 : {
1178 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &YUV422PToGray8);
1179 : }
1180 :
1181 : UniquePtr<ImagePixelLayout>
1182 0 : Utils_Gray8::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
1183 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1184 : {
1185 0 : return CvtYUVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &YUV420PToGray8);
1186 : }
1187 :
1188 : UniquePtr<ImagePixelLayout>
1189 0 : Utils_Gray8::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
1190 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1191 : {
1192 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &NV12ToGray8);
1193 : }
1194 :
1195 : UniquePtr<ImagePixelLayout>
1196 0 : Utils_Gray8::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
1197 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1198 : {
1199 0 : return CvtNVImgToSimpleImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::GRAY8, 1, &NV21ToGray8);
1200 : }
1201 :
1202 : UniquePtr<ImagePixelLayout>
1203 0 : Utils_Gray8::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
1204 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1205 : {
1206 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1207 : }
1208 :
1209 : UniquePtr<ImagePixelLayout>
1210 0 : Utils_Gray8::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
1211 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1212 : {
1213 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1214 : }
1215 :
1216 : UniquePtr<ImagePixelLayout>
1217 0 : Utils_Gray8::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
1218 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1219 : {
1220 0 : return nullptr;
1221 : }
1222 :
1223 : bool
1224 0 : Utils_Gray8::CanConvertFrom(ImageBitmapFormat aSrcFormat)
1225 : {
1226 0 : if (aSrcFormat == ImageBitmapFormat::DEPTH) {
1227 0 : return false;
1228 : }
1229 :
1230 0 : return true;
1231 : }
1232 :
1233 : UniquePtr<ImagePixelLayout>
1234 0 : Utils_Gray8::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
1235 : {
1236 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
1237 : }
1238 :
1239 : /*
1240 : * class Utils_YUV444P.
1241 : */
1242 : /* static */Utils_YUV444P&
1243 0 : Utils_YUV444P::GetInstance()
1244 : {
1245 0 : static Utils_YUV444P instance;
1246 0 : return instance;
1247 : }
1248 :
1249 0 : Utils_YUV444P::Utils_YUV444P()
1250 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
1251 : {
1252 0 : }
1253 :
1254 : uint32_t
1255 0 : Utils_YUV444P::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
1256 : {
1257 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
1258 : }
1259 :
1260 : UniquePtr<ImagePixelLayout>
1261 0 : Utils_YUV444P::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
1262 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1263 : {
1264 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
1265 : }
1266 :
1267 : UniquePtr<ImagePixelLayout>
1268 0 : Utils_YUV444P::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
1269 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1270 : {
1271 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV444P, &RGBA32ToYUV444P);
1272 : }
1273 :
1274 : UniquePtr<ImagePixelLayout>
1275 0 : Utils_YUV444P::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
1276 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1277 : {
1278 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV444P, &libyuv::ARGBToI444);
1279 : }
1280 :
1281 : UniquePtr<ImagePixelLayout>
1282 0 : Utils_YUV444P::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
1283 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1284 : {
1285 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV444P, &RGB24ToYUV444P);
1286 : }
1287 :
1288 : UniquePtr<ImagePixelLayout>
1289 0 : Utils_YUV444P::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
1290 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1291 : {
1292 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV444P, &BGR24ToYUV444P);
1293 : }
1294 :
1295 : UniquePtr<ImagePixelLayout>
1296 0 : Utils_YUV444P::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
1297 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1298 : {
1299 0 : return nullptr;
1300 : }
1301 :
1302 : UniquePtr<ImagePixelLayout>
1303 0 : Utils_YUV444P::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
1304 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1305 : {
1306 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV444P);
1307 : }
1308 :
1309 : // TODO: optimize me.
1310 : UniquePtr<ImagePixelLayout>
1311 0 : Utils_YUV444P::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
1312 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1313 : {
1314 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1315 : }
1316 :
1317 : UniquePtr<ImagePixelLayout>
1318 0 : Utils_YUV444P::ConvertFrom(Utils_YUV420P*, const uint8_t* aSrcBuffer,
1319 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1320 : {
1321 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1322 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1323 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1324 :
1325 : UniquePtr<ImagePixelLayout> layout =
1326 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1327 0 : (*aSrcLayout)[0].mHeight,
1328 0 : (*aSrcLayout)[0].mWidth);
1329 :
1330 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV444P");
1331 :
1332 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1333 :
1334 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1335 :
1336 0 : int rv = I420ToI444(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1337 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1338 0 : aSrcBuffer + srcChannels[2].mOffset, srcChannels[2].mStride,
1339 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1340 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1341 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
1342 0 : channels[0].mWidth, channels[0].mHeight);
1343 :
1344 0 : if (NS_WARN_IF(rv != 0)) {
1345 0 : return nullptr;
1346 : }
1347 :
1348 0 : return layout;
1349 : }
1350 :
1351 : // TODO: optimize me.
1352 : UniquePtr<ImagePixelLayout>
1353 0 : Utils_YUV444P::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
1354 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1355 : {
1356 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1357 : }
1358 :
1359 : // TODO: optimize me.
1360 : UniquePtr<ImagePixelLayout>
1361 0 : Utils_YUV444P::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
1362 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1363 : {
1364 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1365 : }
1366 :
1367 : UniquePtr<ImagePixelLayout>
1368 0 : Utils_YUV444P::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
1369 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1370 : {
1371 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1372 : }
1373 :
1374 : UniquePtr<ImagePixelLayout>
1375 0 : Utils_YUV444P::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
1376 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1377 : {
1378 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1379 : }
1380 :
1381 : UniquePtr<ImagePixelLayout>
1382 0 : Utils_YUV444P::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
1383 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1384 : {
1385 0 : return nullptr;
1386 : }
1387 :
1388 : bool
1389 0 : Utils_YUV444P::CanConvertFrom(ImageBitmapFormat aSrcFormat)
1390 : {
1391 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
1392 : aSrcFormat == ImageBitmapFormat::DEPTH) {
1393 0 : return false;
1394 : }
1395 :
1396 0 : return true;
1397 : }
1398 :
1399 : UniquePtr<ImagePixelLayout>
1400 0 : Utils_YUV444P::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
1401 : {
1402 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(mChannels));
1403 :
1404 : // set mChannels
1405 0 : ChannelPixelLayout* ychannel = layout->AppendElement();
1406 0 : ChannelPixelLayout* uchannel = layout->AppendElement();
1407 0 : ChannelPixelLayout* vchannel = layout->AppendElement();
1408 0 : ychannel->mOffset = 0;
1409 0 : ychannel->mWidth = aWidth;
1410 0 : ychannel->mHeight = aHeight;
1411 0 : ychannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1412 0 : ychannel->mStride = aStride;
1413 0 : ychannel->mSkip = 0; // aYSkip;
1414 :
1415 0 : uchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight;
1416 0 : uchannel->mWidth = aWidth;
1417 0 : uchannel->mHeight = aHeight;
1418 0 : uchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1419 0 : uchannel->mStride = aStride;
1420 0 : uchannel->mSkip = 0; // aUSkip;
1421 :
1422 0 : vchannel->mOffset = uchannel->mOffset + uchannel->mStride * uchannel->mHeight;
1423 0 : vchannel->mWidth = aWidth;
1424 0 : vchannel->mHeight = aHeight;
1425 0 : vchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1426 0 : vchannel->mStride = aStride;
1427 0 : vchannel->mSkip = 0; // aVSkip;
1428 :
1429 0 : return layout;
1430 : }
1431 :
1432 : /*
1433 : * class Utils_YUV422P.
1434 : */
1435 : /* static */Utils_YUV422P&
1436 0 : Utils_YUV422P::GetInstance()
1437 : {
1438 0 : static Utils_YUV422P instance;
1439 0 : return instance;
1440 : }
1441 :
1442 0 : Utils_YUV422P::Utils_YUV422P()
1443 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
1444 : {
1445 0 : }
1446 :
1447 : uint32_t
1448 0 : Utils_YUV422P::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
1449 : {
1450 0 : return aWidth * aHeight * mBytesPerPixelValue +
1451 0 : 2 * ((aWidth + 1) / 2) * aHeight * mBytesPerPixelValue;
1452 : }
1453 :
1454 : UniquePtr<ImagePixelLayout>
1455 0 : Utils_YUV422P::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
1456 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1457 : {
1458 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
1459 : }
1460 :
1461 : UniquePtr<ImagePixelLayout>
1462 0 : Utils_YUV422P::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
1463 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1464 : {
1465 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV422P, &RGBA32ToYUV422P);
1466 : }
1467 :
1468 : UniquePtr<ImagePixelLayout>
1469 0 : Utils_YUV422P::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
1470 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1471 : {
1472 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV422P, &libyuv::ARGBToI422);
1473 : }
1474 :
1475 : UniquePtr<ImagePixelLayout>
1476 0 : Utils_YUV422P::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
1477 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1478 : {
1479 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV422P, &RGB24ToYUV422P);
1480 : }
1481 :
1482 : UniquePtr<ImagePixelLayout>
1483 0 : Utils_YUV422P::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
1484 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1485 : {
1486 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV422P, &BGR24ToYUV422P);
1487 : }
1488 :
1489 : UniquePtr<ImagePixelLayout>
1490 0 : Utils_YUV422P::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
1491 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1492 : {
1493 0 : return nullptr;
1494 : }
1495 :
1496 : // TODO: optimize me.
1497 : UniquePtr<ImagePixelLayout>
1498 0 : Utils_YUV422P::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
1499 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1500 : {
1501 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1502 : }
1503 :
1504 : UniquePtr<ImagePixelLayout>
1505 0 : Utils_YUV422P::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
1506 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1507 : {
1508 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV422P);
1509 : }
1510 :
1511 : UniquePtr<ImagePixelLayout>
1512 0 : Utils_YUV422P::ConvertFrom(Utils_YUV420P*, const uint8_t* aSrcBuffer,
1513 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1514 : {
1515 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1516 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1517 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1518 :
1519 : UniquePtr<ImagePixelLayout> layout =
1520 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1521 0 : (*aSrcLayout)[0].mHeight,
1522 0 : (*aSrcLayout)[0].mWidth);
1523 :
1524 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV422P");
1525 :
1526 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1527 :
1528 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1529 :
1530 0 : libyuv::I420ToI422(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1531 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1532 0 : aSrcBuffer + srcChannels[2].mOffset, srcChannels[2].mStride,
1533 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1534 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1535 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
1536 0 : channels[0].mWidth, channels[0].mHeight);
1537 :
1538 0 : return layout;
1539 : }
1540 :
1541 : // TODO: optimize me.
1542 : UniquePtr<ImagePixelLayout>
1543 0 : Utils_YUV422P::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
1544 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1545 : {
1546 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1547 : }
1548 :
1549 : // TODO: optimize me.
1550 : UniquePtr<ImagePixelLayout>
1551 0 : Utils_YUV422P::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
1552 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1553 : {
1554 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1555 : }
1556 :
1557 : UniquePtr<ImagePixelLayout>
1558 0 : Utils_YUV422P::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
1559 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1560 : {
1561 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1562 : }
1563 :
1564 : UniquePtr<ImagePixelLayout>
1565 0 : Utils_YUV422P::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
1566 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1567 : {
1568 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1569 : }
1570 :
1571 : UniquePtr<ImagePixelLayout>
1572 0 : Utils_YUV422P::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
1573 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1574 : {
1575 0 : return nullptr;
1576 : }
1577 :
1578 : bool
1579 0 : Utils_YUV422P::CanConvertFrom(ImageBitmapFormat aSrcFormat)
1580 : {
1581 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
1582 : aSrcFormat == ImageBitmapFormat::DEPTH) {
1583 0 : return false;
1584 : }
1585 :
1586 0 : return true;
1587 : }
1588 :
1589 : UniquePtr<ImagePixelLayout>
1590 0 : Utils_YUV422P::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
1591 : {
1592 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(mChannels));
1593 :
1594 : // set mChannels
1595 0 : ChannelPixelLayout* ychannel = layout->AppendElement();
1596 0 : ChannelPixelLayout* uchannel = layout->AppendElement();
1597 0 : ChannelPixelLayout* vchannel = layout->AppendElement();
1598 0 : ychannel->mOffset = 0;
1599 0 : ychannel->mWidth = aWidth;
1600 0 : ychannel->mHeight = aHeight;
1601 0 : ychannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1602 0 : ychannel->mStride = aStride;
1603 0 : ychannel->mSkip = 0; // aYSkip;
1604 :
1605 0 : uchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight;
1606 0 : uchannel->mWidth = (aWidth + 1) / 2;
1607 0 : uchannel->mHeight = aHeight;
1608 0 : uchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1609 0 : uchannel->mStride = (aStride + 1) / 2;
1610 0 : uchannel->mSkip = 0; // aUSkip;
1611 :
1612 0 : vchannel->mOffset = uchannel->mOffset + uchannel->mStride * uchannel->mHeight;
1613 0 : vchannel->mWidth = (aWidth + 1) / 2;
1614 0 : vchannel->mHeight = aHeight;
1615 0 : vchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1616 0 : vchannel->mStride = (aStride + 1) / 2;
1617 0 : vchannel->mSkip = 0; // aVSkip;
1618 :
1619 0 : return layout;
1620 : }
1621 :
1622 : /*
1623 : * Utils_YUV420P.
1624 : */
1625 : /* static */Utils_YUV420P&
1626 0 : Utils_YUV420P::GetInstance()
1627 : {
1628 0 : static Utils_YUV420P instance;
1629 0 : return instance;
1630 : }
1631 :
1632 0 : Utils_YUV420P::Utils_YUV420P()
1633 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
1634 : {
1635 0 : }
1636 :
1637 : uint32_t
1638 0 : Utils_YUV420P::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
1639 : {
1640 0 : return aWidth * aHeight * mBytesPerPixelValue +
1641 0 : 2 * ((aWidth + 1) / 2) * ((aHeight + 1) / 2) * mBytesPerPixelValue;
1642 : }
1643 :
1644 : UniquePtr<ImagePixelLayout>
1645 0 : Utils_YUV420P::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
1646 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1647 : {
1648 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
1649 : }
1650 :
1651 : UniquePtr<ImagePixelLayout>
1652 0 : Utils_YUV420P::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
1653 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1654 : {
1655 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, &libyuv::ABGRToI420);
1656 : }
1657 :
1658 : UniquePtr<ImagePixelLayout>
1659 0 : Utils_YUV420P::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
1660 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1661 : {
1662 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, &libyuv::ARGBToI420);
1663 : }
1664 :
1665 : UniquePtr<ImagePixelLayout>
1666 0 : Utils_YUV420P::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
1667 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1668 : {
1669 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, &RGB24ToYUV420P);
1670 : }
1671 :
1672 : UniquePtr<ImagePixelLayout>
1673 0 : Utils_YUV420P::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
1674 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1675 : {
1676 0 : return CvtSimpleImgToYUVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, &BGR24ToYUV420P);
1677 : }
1678 :
1679 : UniquePtr<ImagePixelLayout>
1680 0 : Utils_YUV420P::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
1681 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1682 : {
1683 0 : return nullptr;
1684 : }
1685 :
1686 : UniquePtr<ImagePixelLayout>
1687 0 : Utils_YUV420P::ConvertFrom(Utils_YUV444P*, const uint8_t* aSrcBuffer,
1688 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1689 : {
1690 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1691 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1692 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1693 :
1694 : UniquePtr<ImagePixelLayout> layout =
1695 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1696 0 : (*aSrcLayout)[0].mHeight,
1697 0 : (*aSrcLayout)[0].mWidth);
1698 :
1699 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV420P");
1700 :
1701 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1702 :
1703 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1704 :
1705 0 : libyuv::I444ToI420(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1706 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1707 0 : aSrcBuffer + srcChannels[2].mOffset, srcChannels[2].mStride,
1708 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1709 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1710 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
1711 0 : channels[0].mWidth, channels[0].mHeight);
1712 :
1713 0 : return layout;
1714 : }
1715 :
1716 : UniquePtr<ImagePixelLayout>
1717 0 : Utils_YUV420P::ConvertFrom(Utils_YUV422P*, const uint8_t* aSrcBuffer,
1718 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1719 : {
1720 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1721 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1722 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1723 :
1724 : UniquePtr<ImagePixelLayout> layout =
1725 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1726 0 : (*aSrcLayout)[0].mHeight,
1727 0 : (*aSrcLayout)[0].mWidth);
1728 :
1729 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV420P");
1730 :
1731 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1732 :
1733 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1734 :
1735 0 : libyuv::I422ToI420(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1736 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1737 0 : aSrcBuffer + srcChannels[2].mOffset, srcChannels[2].mStride,
1738 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1739 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1740 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
1741 0 : channels[0].mWidth, channels[0].mHeight);
1742 :
1743 0 : return layout;
1744 : }
1745 :
1746 : UniquePtr<ImagePixelLayout>
1747 0 : Utils_YUV420P::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
1748 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1749 : {
1750 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P);
1751 : }
1752 :
1753 : UniquePtr<ImagePixelLayout>
1754 0 : Utils_YUV420P::ConvertFrom(Utils_YUV420SP_NV12*, const uint8_t* aSrcBuffer,
1755 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1756 : {
1757 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1758 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1759 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1760 :
1761 : UniquePtr<ImagePixelLayout> layout =
1762 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1763 0 : (*aSrcLayout)[0].mHeight,
1764 0 : (*aSrcLayout)[0].mWidth);
1765 :
1766 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV420P");
1767 :
1768 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1769 :
1770 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1771 :
1772 0 : libyuv::NV12ToI420(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1773 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1774 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1775 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1776 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
1777 0 : channels[0].mWidth, channels[0].mHeight);
1778 :
1779 0 : return layout;
1780 : }
1781 :
1782 : UniquePtr<ImagePixelLayout>
1783 0 : Utils_YUV420P::ConvertFrom(Utils_YUV420SP_NV21*, const uint8_t* aSrcBuffer,
1784 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1785 : {
1786 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1787 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1788 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1789 :
1790 : UniquePtr<ImagePixelLayout> layout =
1791 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1792 0 : (*aSrcLayout)[0].mHeight,
1793 0 : (*aSrcLayout)[0].mWidth);
1794 :
1795 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV420P");
1796 :
1797 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1798 :
1799 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1800 :
1801 0 : libyuv::NV21ToI420(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1802 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1803 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1804 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1805 0 : aDstBuffer + channels[2].mOffset, channels[2].mStride,
1806 0 : channels[0].mWidth, channels[0].mHeight);
1807 :
1808 0 : return layout;
1809 : }
1810 :
1811 : UniquePtr<ImagePixelLayout>
1812 0 : Utils_YUV420P::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
1813 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1814 : {
1815 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1816 : }
1817 :
1818 : UniquePtr<ImagePixelLayout>
1819 0 : Utils_YUV420P::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
1820 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1821 : {
1822 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
1823 : }
1824 :
1825 : UniquePtr<ImagePixelLayout>
1826 0 : Utils_YUV420P::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
1827 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1828 : {
1829 0 : return nullptr;
1830 : }
1831 :
1832 : bool
1833 0 : Utils_YUV420P::CanConvertFrom(ImageBitmapFormat aSrcFormat)
1834 : {
1835 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
1836 : aSrcFormat == ImageBitmapFormat::DEPTH) {
1837 0 : return false;
1838 : }
1839 :
1840 0 : return true;
1841 : }
1842 :
1843 : UniquePtr<ImagePixelLayout>
1844 0 : Utils_YUV420P::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
1845 : {
1846 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(mChannels));
1847 :
1848 : // set mChannels
1849 0 : ChannelPixelLayout* ychannel = layout->AppendElement();
1850 0 : ChannelPixelLayout* uchannel = layout->AppendElement();
1851 0 : ChannelPixelLayout* vchannel = layout->AppendElement();
1852 0 : ychannel->mOffset = 0;
1853 0 : ychannel->mWidth = aWidth;
1854 0 : ychannel->mHeight = aHeight;
1855 0 : ychannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1856 0 : ychannel->mStride = aStride;
1857 0 : ychannel->mSkip = 0; // aYSkip;
1858 :
1859 0 : uchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight;
1860 0 : uchannel->mWidth = (aWidth + 1) / 2;
1861 0 : uchannel->mHeight = (aHeight + 1) / 2;
1862 0 : uchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1863 0 : uchannel->mStride = (aStride + 1) / 2;
1864 0 : uchannel->mSkip = 0; // aUSkip;
1865 :
1866 0 : vchannel->mOffset = uchannel->mOffset + uchannel->mStride * uchannel->mHeight;
1867 0 : vchannel->mWidth = (aWidth + 1) / 2;
1868 0 : vchannel->mHeight = (aHeight + 1) / 2;
1869 0 : vchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
1870 0 : vchannel->mStride = (aStride + 1) / 2;
1871 0 : vchannel->mSkip = 0; // aVSkip;
1872 :
1873 0 : return layout;
1874 : }
1875 :
1876 : /*
1877 : * class Utils_YUV420SP_NV12.
1878 : */
1879 : /* static */Utils_YUV420SP_NV12&
1880 0 : Utils_YUV420SP_NV12::GetInstance()
1881 : {
1882 0 : static Utils_YUV420SP_NV12 instance;
1883 0 : return instance;
1884 : }
1885 :
1886 0 : Utils_YUV420SP_NV12::Utils_YUV420SP_NV12()
1887 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
1888 : {
1889 0 : }
1890 :
1891 : uint32_t
1892 0 : Utils_YUV420SP_NV12::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
1893 : {
1894 0 : return aWidth * aHeight * mBytesPerPixelValue +
1895 0 : 2 * ((aWidth + 1) / 2) * ((aHeight + 1) / 2) * mBytesPerPixelValue;
1896 : }
1897 :
1898 : UniquePtr<ImagePixelLayout>
1899 0 : Utils_YUV420SP_NV12::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
1900 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1901 : {
1902 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
1903 : }
1904 :
1905 : UniquePtr<ImagePixelLayout>
1906 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
1907 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1908 : {
1909 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV12, &RGBA32ToNV12);
1910 : }
1911 :
1912 : UniquePtr<ImagePixelLayout>
1913 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
1914 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1915 : {
1916 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV12, &libyuv::ARGBToNV12);
1917 : }
1918 :
1919 : UniquePtr<ImagePixelLayout>
1920 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
1921 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1922 : {
1923 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV12, &RGB24ToNV12);
1924 : }
1925 :
1926 : UniquePtr<ImagePixelLayout>
1927 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
1928 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1929 : {
1930 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV12, &BGR24ToNV12);
1931 : }
1932 :
1933 : UniquePtr<ImagePixelLayout>
1934 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
1935 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1936 : {
1937 0 : return nullptr;
1938 : }
1939 :
1940 : // TODO: optimize me.
1941 : UniquePtr<ImagePixelLayout>
1942 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
1943 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1944 : {
1945 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1946 : }
1947 :
1948 : // TODO: optimize me.
1949 : UniquePtr<ImagePixelLayout>
1950 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
1951 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1952 : {
1953 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1954 : }
1955 :
1956 : UniquePtr<ImagePixelLayout>
1957 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_YUV420P*, const uint8_t* aSrcBuffer,
1958 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1959 : {
1960 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
1961 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
1962 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
1963 :
1964 : UniquePtr<ImagePixelLayout> layout =
1965 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
1966 0 : (*aSrcLayout)[0].mHeight,
1967 0 : (*aSrcLayout)[0].mWidth);
1968 :
1969 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV420SP_NV12");
1970 :
1971 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
1972 :
1973 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
1974 :
1975 0 : libyuv::I420ToNV12(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
1976 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
1977 0 : aSrcBuffer + srcChannels[2].mOffset, srcChannels[2].mStride,
1978 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
1979 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
1980 0 : channels[0].mWidth, channels[0].mHeight);
1981 :
1982 0 : return layout;
1983 : }
1984 :
1985 : UniquePtr<ImagePixelLayout>
1986 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
1987 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1988 : {
1989 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV12);
1990 : }
1991 :
1992 : // TODO: optimize me.
1993 : UniquePtr<ImagePixelLayout>
1994 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
1995 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
1996 : {
1997 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
1998 : }
1999 :
2000 : UniquePtr<ImagePixelLayout>
2001 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
2002 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2003 : {
2004 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2005 : }
2006 :
2007 : UniquePtr<ImagePixelLayout>
2008 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
2009 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2010 : {
2011 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2012 : }
2013 :
2014 : UniquePtr<ImagePixelLayout>
2015 0 : Utils_YUV420SP_NV12::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
2016 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2017 : {
2018 0 : return nullptr;
2019 : }
2020 :
2021 : bool
2022 0 : Utils_YUV420SP_NV12::CanConvertFrom(ImageBitmapFormat aSrcFormat)
2023 : {
2024 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
2025 : aSrcFormat == ImageBitmapFormat::DEPTH) {
2026 0 : return false;
2027 : }
2028 :
2029 0 : return true;
2030 : }
2031 :
2032 : UniquePtr<ImagePixelLayout>
2033 0 : Utils_YUV420SP_NV12::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
2034 : {
2035 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(mChannels));
2036 :
2037 : // set mChannels
2038 0 : ChannelPixelLayout* ychannel = layout->AppendElement();
2039 0 : ChannelPixelLayout* uchannel = layout->AppendElement();
2040 0 : ChannelPixelLayout* vchannel = layout->AppendElement();
2041 0 : ychannel->mOffset = 0;
2042 0 : ychannel->mWidth = aWidth;
2043 0 : ychannel->mHeight = aHeight;
2044 0 : ychannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2045 0 : ychannel->mStride = aStride;
2046 0 : ychannel->mSkip = 0; // aYSkip;
2047 :
2048 0 : uchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight;
2049 0 : uchannel->mWidth = (aWidth + 1) / 2;
2050 0 : uchannel->mHeight = (aHeight + 1) / 2;
2051 0 : uchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2052 0 : uchannel->mStride = uchannel->mWidth * 2;
2053 0 : uchannel->mSkip = 1; // aUSkip;
2054 :
2055 0 : vchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight + 1;
2056 0 : vchannel->mWidth = (aWidth + 1) / 2;
2057 0 : vchannel->mHeight = (aHeight + 1) / 2;
2058 0 : vchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2059 0 : vchannel->mStride = vchannel->mWidth * 2;
2060 0 : vchannel->mSkip = 1; // aVSkip;
2061 :
2062 0 : return layout;
2063 : }
2064 :
2065 : /*
2066 : * class Utils_YUV420SP_NV21.
2067 : */
2068 : /* static */Utils_YUV420SP_NV21&
2069 0 : Utils_YUV420SP_NV21::GetInstance()
2070 : {
2071 0 : static Utils_YUV420SP_NV21 instance;
2072 0 : return instance;
2073 : }
2074 :
2075 0 : Utils_YUV420SP_NV21::Utils_YUV420SP_NV21()
2076 0 : : Utils(3, ChannelPixelLayoutDataType::Uint8)
2077 : {
2078 0 : }
2079 :
2080 : uint32_t
2081 0 : Utils_YUV420SP_NV21::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
2082 : {
2083 0 : return aWidth * aHeight * mBytesPerPixelValue +
2084 0 : 2 * ((aWidth + 1) / 2) * ((aHeight + 1) / 2) * mBytesPerPixelValue;
2085 : }
2086 :
2087 : UniquePtr<ImagePixelLayout>
2088 0 : Utils_YUV420SP_NV21::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
2089 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2090 : {
2091 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
2092 : }
2093 :
2094 : UniquePtr<ImagePixelLayout>
2095 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
2096 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2097 : {
2098 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV21, &RGBA32ToNV21);
2099 : }
2100 :
2101 : UniquePtr<ImagePixelLayout>
2102 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
2103 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2104 : {
2105 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV21, &libyuv::ARGBToNV21);
2106 : }
2107 :
2108 : UniquePtr<ImagePixelLayout>
2109 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
2110 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2111 : {
2112 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV21, &RGB24ToNV21);
2113 : }
2114 :
2115 : UniquePtr<ImagePixelLayout>
2116 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
2117 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2118 : {
2119 0 : return CvtSimpleImgToNVImg(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV21, &BGR24ToNV21);
2120 : }
2121 :
2122 : UniquePtr<ImagePixelLayout>
2123 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
2124 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2125 : {
2126 0 : return nullptr;
2127 : }
2128 :
2129 : // TODO: optimize me.
2130 : UniquePtr<ImagePixelLayout>
2131 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
2132 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2133 : {
2134 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
2135 : }
2136 :
2137 : // TODO: optimize me.
2138 : UniquePtr<ImagePixelLayout>
2139 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
2140 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2141 : {
2142 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
2143 : }
2144 :
2145 : UniquePtr<ImagePixelLayout>
2146 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_YUV420P*, const uint8_t* aSrcBuffer,
2147 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2148 : {
2149 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
2150 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
2151 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
2152 :
2153 : UniquePtr<ImagePixelLayout> layout =
2154 0 : CreateDefaultLayout((*aSrcLayout)[0].mWidth,
2155 0 : (*aSrcLayout)[0].mHeight,
2156 0 : (*aSrcLayout)[0].mWidth);
2157 :
2158 0 : MOZ_ASSERT(layout, "Cannot create a ImagePixelLayout of YUV420SP_NV21");
2159 :
2160 0 : const nsTArray<ChannelPixelLayout>& channels = *layout;
2161 :
2162 0 : const nsTArray<ChannelPixelLayout>& srcChannels = *aSrcLayout;
2163 :
2164 0 : libyuv::I420ToNV21(aSrcBuffer + srcChannels[0].mOffset, srcChannels[0].mStride,
2165 0 : aSrcBuffer + srcChannels[1].mOffset, srcChannels[1].mStride,
2166 0 : aSrcBuffer + srcChannels[2].mOffset, srcChannels[2].mStride,
2167 0 : aDstBuffer + channels[0].mOffset, channels[0].mStride,
2168 0 : aDstBuffer + channels[1].mOffset, channels[1].mStride,
2169 0 : channels[0].mWidth, channels[0].mHeight);
2170 :
2171 0 : return layout;
2172 : }
2173 :
2174 : // TODO: optimize me.
2175 : UniquePtr<ImagePixelLayout>
2176 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
2177 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2178 : {
2179 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420P, this);
2180 : }
2181 :
2182 : UniquePtr<ImagePixelLayout>
2183 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
2184 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2185 : {
2186 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::YUV420SP_NV21);
2187 : }
2188 :
2189 : UniquePtr<ImagePixelLayout>
2190 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
2191 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2192 : {
2193 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2194 : }
2195 :
2196 : UniquePtr<ImagePixelLayout>
2197 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
2198 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2199 : {
2200 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2201 : }
2202 :
2203 : UniquePtr<ImagePixelLayout>
2204 0 : Utils_YUV420SP_NV21::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
2205 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2206 : {
2207 0 : return nullptr;
2208 : }
2209 :
2210 : bool
2211 0 : Utils_YUV420SP_NV21::CanConvertFrom(ImageBitmapFormat aSrcFormat)
2212 : {
2213 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
2214 : aSrcFormat == ImageBitmapFormat::DEPTH) {
2215 0 : return false;
2216 : }
2217 :
2218 0 : return true;
2219 : }
2220 :
2221 : UniquePtr<ImagePixelLayout>
2222 0 : Utils_YUV420SP_NV21::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
2223 : {
2224 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(mChannels));
2225 :
2226 : // set mChannels
2227 0 : ChannelPixelLayout* ychannel = layout->AppendElement();
2228 0 : ChannelPixelLayout* vchannel = layout->AppendElement(); // v is the 2nd channel.
2229 0 : ChannelPixelLayout* uchannel = layout->AppendElement(); // u is the 3rd channel.
2230 0 : ychannel->mOffset = 0;
2231 0 : ychannel->mWidth = aWidth;
2232 0 : ychannel->mHeight = aHeight;
2233 0 : ychannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2234 0 : ychannel->mStride = aStride;
2235 0 : ychannel->mSkip = 0; // aYSkip;
2236 :
2237 0 : vchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight;
2238 0 : vchannel->mWidth = (aWidth + 1) / 2;
2239 0 : vchannel->mHeight = (aHeight + 1) / 2;
2240 0 : vchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2241 0 : vchannel->mStride = vchannel->mWidth * 2;
2242 0 : vchannel->mSkip = 1; // aVSkip;
2243 :
2244 0 : uchannel->mOffset = ychannel->mOffset + ychannel->mStride * ychannel->mHeight + 1;
2245 0 : uchannel->mWidth = (aWidth + 1) / 2;
2246 0 : uchannel->mHeight = (aHeight + 1) / 2;
2247 0 : uchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2248 0 : uchannel->mStride = uchannel->mWidth * 2;
2249 0 : uchannel->mSkip = 1; // aUSkip;
2250 :
2251 0 : return layout;
2252 : }
2253 :
2254 : /*
2255 : * Utils_HSV.
2256 : */
2257 : /* static */Utils_HSV&
2258 0 : Utils_HSV::GetInstance()
2259 : {
2260 0 : static Utils_HSV instance;
2261 0 : return instance;
2262 : }
2263 :
2264 0 : Utils_HSV::Utils_HSV()
2265 0 : : Utils(3, ChannelPixelLayoutDataType::Float32)
2266 : {
2267 0 : }
2268 :
2269 : uint32_t
2270 0 : Utils_HSV::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
2271 : {
2272 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
2273 : }
2274 :
2275 : UniquePtr<ImagePixelLayout>
2276 0 : Utils_HSV::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
2277 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2278 : {
2279 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
2280 : }
2281 :
2282 : UniquePtr<ImagePixelLayout>
2283 0 : Utils_HSV::ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer,
2284 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2285 : {
2286 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcFormat, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::HSV, 3, &RGBA32ToHSV);
2287 : }
2288 :
2289 : UniquePtr<ImagePixelLayout>
2290 0 : Utils_HSV::ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer,
2291 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2292 : {
2293 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcFormat, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::HSV, 3, &BGRA32ToHSV);
2294 : }
2295 :
2296 : UniquePtr<ImagePixelLayout>
2297 0 : Utils_HSV::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
2298 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2299 : {
2300 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcUtils, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::HSV, 3, &RGB24ToHSV);
2301 : }
2302 :
2303 : UniquePtr<ImagePixelLayout>
2304 0 : Utils_HSV::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
2305 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2306 : {
2307 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcUtils, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::HSV, 3, &BGR24ToHSV);
2308 : }
2309 :
2310 : UniquePtr<ImagePixelLayout>
2311 0 : Utils_HSV::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
2312 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2313 : {
2314 0 : return nullptr;
2315 : }
2316 :
2317 : UniquePtr<ImagePixelLayout>
2318 0 : Utils_HSV::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
2319 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2320 : {
2321 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2322 : }
2323 :
2324 : UniquePtr<ImagePixelLayout>
2325 0 : Utils_HSV::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
2326 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2327 : {
2328 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2329 : }
2330 :
2331 : UniquePtr<ImagePixelLayout>
2332 0 : Utils_HSV::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
2333 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2334 : {
2335 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2336 : }
2337 :
2338 : UniquePtr<ImagePixelLayout>
2339 0 : Utils_HSV::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
2340 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2341 : {
2342 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2343 : }
2344 :
2345 : UniquePtr<ImagePixelLayout>
2346 0 : Utils_HSV::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
2347 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2348 : {
2349 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2350 : }
2351 :
2352 : UniquePtr<ImagePixelLayout>
2353 0 : Utils_HSV::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
2354 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2355 : {
2356 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::HSV);
2357 : }
2358 :
2359 : UniquePtr<ImagePixelLayout>
2360 0 : Utils_HSV::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
2361 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2362 : {
2363 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2364 : }
2365 :
2366 : UniquePtr<ImagePixelLayout>
2367 0 : Utils_HSV::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
2368 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2369 : {
2370 0 : return nullptr;
2371 : }
2372 :
2373 : bool
2374 0 : Utils_HSV::CanConvertFrom(ImageBitmapFormat aSrcFormat)
2375 : {
2376 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
2377 : aSrcFormat == ImageBitmapFormat::DEPTH) {
2378 0 : return false;
2379 : }
2380 :
2381 0 : return true;
2382 : }
2383 :
2384 : UniquePtr<ImagePixelLayout>
2385 0 : Utils_HSV::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
2386 : {
2387 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
2388 : }
2389 :
2390 : /*
2391 : * Utils_Lab.
2392 : */
2393 : /* static */Utils_Lab&
2394 0 : Utils_Lab::GetInstance()
2395 : {
2396 0 : static Utils_Lab instance;
2397 0 : return instance;
2398 : }
2399 :
2400 0 : Utils_Lab::Utils_Lab()
2401 0 : : Utils(3, ChannelPixelLayoutDataType::Float32)
2402 : {
2403 0 : }
2404 :
2405 : uint32_t
2406 0 : Utils_Lab::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
2407 : {
2408 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
2409 : }
2410 :
2411 : UniquePtr<ImagePixelLayout>
2412 0 : Utils_Lab::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
2413 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2414 : {
2415 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
2416 : }
2417 :
2418 : UniquePtr<ImagePixelLayout>
2419 0 : Utils_Lab::ConvertFrom(Utils_RGBA32* aSrcUtils, const uint8_t* aSrcBuffer,
2420 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2421 : {
2422 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcUtils, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::Lab, 3, &RGBA32ToLab);
2423 : }
2424 :
2425 : UniquePtr<ImagePixelLayout>
2426 0 : Utils_Lab::ConvertFrom(Utils_BGRA32* aSrcUtils, const uint8_t* aSrcBuffer,
2427 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2428 : {
2429 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcUtils, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::Lab, 3, &BGRA32ToLab);
2430 : }
2431 :
2432 : UniquePtr<ImagePixelLayout>
2433 0 : Utils_Lab::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
2434 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2435 : {
2436 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcUtils, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::Lab, 3, &RGB24ToLab);
2437 : }
2438 :
2439 : UniquePtr<ImagePixelLayout>
2440 0 : Utils_Lab::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
2441 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2442 : {
2443 0 : return CvtSimpleImgToSimpleImg<uint8_t, float>(aSrcUtils, aSrcBuffer, aSrcLayout, (float*)aDstBuffer, ImageBitmapFormat::Lab, 3, &BGR24ToLab);
2444 : }
2445 :
2446 : UniquePtr<ImagePixelLayout>
2447 0 : Utils_Lab::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
2448 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2449 : {
2450 0 : return nullptr;
2451 : }
2452 :
2453 : UniquePtr<ImagePixelLayout>
2454 0 : Utils_Lab::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
2455 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2456 : {
2457 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2458 : }
2459 :
2460 : UniquePtr<ImagePixelLayout>
2461 0 : Utils_Lab::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
2462 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2463 : {
2464 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2465 : }
2466 :
2467 : UniquePtr<ImagePixelLayout>
2468 0 : Utils_Lab::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
2469 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2470 : {
2471 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2472 : }
2473 :
2474 : UniquePtr<ImagePixelLayout>
2475 0 : Utils_Lab::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
2476 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2477 : {
2478 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2479 : }
2480 :
2481 : UniquePtr<ImagePixelLayout>
2482 0 : Utils_Lab::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
2483 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2484 : {
2485 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2486 : }
2487 :
2488 : UniquePtr<ImagePixelLayout>
2489 0 : Utils_Lab::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
2490 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2491 : {
2492 0 : return TwoPassConversion(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::RGB24, this);
2493 : }
2494 :
2495 : UniquePtr<ImagePixelLayout>
2496 0 : Utils_Lab::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
2497 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2498 : {
2499 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::Lab);
2500 : }
2501 :
2502 : UniquePtr<ImagePixelLayout>
2503 0 : Utils_Lab::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
2504 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2505 : {
2506 0 : return nullptr;
2507 : }
2508 :
2509 : bool
2510 0 : Utils_Lab::CanConvertFrom(ImageBitmapFormat aSrcFormat)
2511 : {
2512 0 : if (aSrcFormat == ImageBitmapFormat::GRAY8 ||
2513 : aSrcFormat == ImageBitmapFormat::DEPTH) {
2514 0 : return false;
2515 : }
2516 :
2517 0 : return true;
2518 : }
2519 :
2520 : UniquePtr<ImagePixelLayout>
2521 0 : Utils_Lab::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
2522 : {
2523 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
2524 : }
2525 :
2526 : /*
2527 : * Utils_Depth.
2528 : */
2529 : /* static */Utils_Depth&
2530 0 : Utils_Depth::GetInstance()
2531 : {
2532 0 : static Utils_Depth instance;
2533 0 : return instance;
2534 : }
2535 :
2536 0 : Utils_Depth::Utils_Depth()
2537 0 : : Utils(1, ChannelPixelLayoutDataType::Uint16)
2538 : {
2539 0 : }
2540 :
2541 : uint32_t
2542 0 : Utils_Depth::NeededBufferSize(uint32_t aWidth, uint32_t aHeight)
2543 : {
2544 0 : return aWidth * aHeight * (uint32_t)mChannels * mBytesPerPixelValue;
2545 : }
2546 :
2547 : UniquePtr<ImagePixelLayout>
2548 0 : Utils_Depth::ConvertTo(Utils* aDstFormat, const uint8_t* aSrcBuffer,
2549 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2550 : {
2551 0 : return aDstFormat->ConvertFrom(this, aSrcBuffer, aSrcLayout, aDstBuffer);
2552 : }
2553 :
2554 : UniquePtr<ImagePixelLayout>
2555 0 : Utils_Depth::ConvertFrom(Utils_RGBA32* aSrcFormat, const uint8_t* aSrcBuffer,
2556 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2557 : {
2558 0 : return nullptr;
2559 : }
2560 :
2561 : UniquePtr<ImagePixelLayout>
2562 0 : Utils_Depth::ConvertFrom(Utils_BGRA32* aSrcFormat, const uint8_t* aSrcBuffer,
2563 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2564 : {
2565 0 : return nullptr;
2566 : }
2567 :
2568 : UniquePtr<ImagePixelLayout>
2569 0 : Utils_Depth::ConvertFrom(Utils_RGB24* aSrcUtils, const uint8_t* aSrcBuffer,
2570 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2571 : {
2572 0 : return nullptr;
2573 : }
2574 :
2575 : UniquePtr<ImagePixelLayout>
2576 0 : Utils_Depth::ConvertFrom(Utils_BGR24* aSrcUtils, const uint8_t* aSrcBuffer,
2577 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2578 : {
2579 0 : return nullptr;
2580 : }
2581 :
2582 : UniquePtr<ImagePixelLayout>
2583 0 : Utils_Depth::ConvertFrom(Utils_Gray8* aSrcFormat, const uint8_t* aSrcBuffer,
2584 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2585 : {
2586 0 : return nullptr;
2587 : }
2588 :
2589 : UniquePtr<ImagePixelLayout>
2590 0 : Utils_Depth::ConvertFrom(Utils_YUV444P* aSrcUtils, const uint8_t* aSrcBuffer,
2591 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2592 : {
2593 0 : return nullptr;
2594 : }
2595 :
2596 : UniquePtr<ImagePixelLayout>
2597 0 : Utils_Depth::ConvertFrom(Utils_YUV422P* aSrcUtils, const uint8_t* aSrcBuffer,
2598 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2599 : {
2600 0 : return nullptr;
2601 : }
2602 :
2603 : UniquePtr<ImagePixelLayout>
2604 0 : Utils_Depth::ConvertFrom(Utils_YUV420P* aSrcUtils, const uint8_t* aSrcBuffer,
2605 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2606 : {
2607 0 : return nullptr;
2608 : }
2609 :
2610 : UniquePtr<ImagePixelLayout>
2611 0 : Utils_Depth::ConvertFrom(Utils_YUV420SP_NV12* aSrcUtils, const uint8_t* aSrcBuffer,
2612 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2613 : {
2614 0 : return nullptr;
2615 : }
2616 :
2617 : UniquePtr<ImagePixelLayout>
2618 0 : Utils_Depth::ConvertFrom(Utils_YUV420SP_NV21* aSrcUtils, const uint8_t* aSrcBuffer,
2619 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2620 : {
2621 0 : return nullptr;
2622 : }
2623 :
2624 : UniquePtr<ImagePixelLayout>
2625 0 : Utils_Depth::ConvertFrom(Utils_HSV* aSrcUtils, const uint8_t* aSrcBuffer,
2626 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2627 : {
2628 0 : return nullptr;
2629 : }
2630 :
2631 : UniquePtr<ImagePixelLayout>
2632 0 : Utils_Depth::ConvertFrom(Utils_Lab* aSrcUtils, const uint8_t* aSrcBuffer,
2633 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2634 : {
2635 0 : return nullptr;
2636 : }
2637 :
2638 : UniquePtr<ImagePixelLayout>
2639 0 : Utils_Depth::ConvertFrom(Utils_Depth* aSrcUtils, const uint8_t* aSrcBuffer,
2640 : const ImagePixelLayout* aSrcLayout, uint8_t* aDstBuffer)
2641 : {
2642 0 : return PureCopy(aSrcUtils, aSrcBuffer, aSrcLayout, aDstBuffer, ImageBitmapFormat::DEPTH);
2643 : }
2644 :
2645 : bool
2646 0 : Utils_Depth::CanConvertFrom(ImageBitmapFormat aSrcFormat)
2647 : {
2648 0 : if (aSrcFormat == ImageBitmapFormat::DEPTH ) {
2649 0 : return true;
2650 : }
2651 :
2652 0 : return false;
2653 : }
2654 :
2655 : UniquePtr<ImagePixelLayout>
2656 0 : Utils_Depth::CreateDefaultLayout(uint32_t aWidth, uint32_t aHeight, uint32_t aStride)
2657 : {
2658 0 : return CreateDefaultLayoutForSimpleImage(aWidth, aHeight, aStride, mChannels, mBytesPerPixelValue, mDataType);
2659 : }
2660 :
2661 : } // namespace imagebitmapformat
2662 :
2663 : /*
2664 : * Global functions.
2665 : */
2666 :
2667 : using namespace mozilla::dom::imagebitmapformat;
2668 :
2669 : UniquePtr<ImagePixelLayout>
2670 0 : CreateDefaultPixelLayout(ImageBitmapFormat aFormat, uint32_t aWidth,
2671 : uint32_t aHeight, uint32_t aStride)
2672 : {
2673 0 : UtilsUniquePtr format = Utils::GetUtils(aFormat);
2674 0 : MOZ_ASSERT(format, "Cannot get a valid ImageBitmapFormatUtils instance.");
2675 :
2676 0 : return format->CreateDefaultLayout(aWidth, aHeight, aStride);
2677 : }
2678 :
2679 : UniquePtr<ImagePixelLayout>
2680 0 : CreatePixelLayoutFromPlanarYCbCrData(const layers::PlanarYCbCrData* aData)
2681 : {
2682 0 : if (!aData) {
2683 : // something wrong
2684 0 : return nullptr;
2685 : }
2686 :
2687 0 : UniquePtr<ImagePixelLayout> layout(new ImagePixelLayout(3));
2688 :
2689 0 : ChannelPixelLayout* ychannel = layout->AppendElement();
2690 0 : ChannelPixelLayout* uchannel = layout->AppendElement();
2691 0 : ChannelPixelLayout* vchannel = layout->AppendElement();
2692 :
2693 0 : ychannel->mOffset = 0;
2694 :
2695 0 : if (aData->mCrChannel - aData->mCbChannel > 0) {
2696 0 : uchannel->mOffset = ychannel->mOffset + (aData->mCbChannel - aData->mYChannel);
2697 0 : vchannel->mOffset = uchannel->mOffset + (aData->mCrChannel - aData->mCbChannel);
2698 : } else {
2699 0 : uchannel->mOffset = ychannel->mOffset + (aData->mCrChannel - aData->mYChannel);
2700 0 : vchannel->mOffset = uchannel->mOffset + (aData->mCbChannel - aData->mCrChannel);
2701 : }
2702 :
2703 0 : ychannel->mWidth = aData->mYSize.width;
2704 0 : ychannel->mHeight = aData->mYSize.height;
2705 0 : ychannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2706 0 : ychannel->mStride = aData->mYStride;
2707 0 : ychannel->mSkip = aData->mYSkip;
2708 :
2709 0 : uchannel->mWidth = aData->mCbCrSize.width;
2710 0 : uchannel->mHeight = aData->mCbCrSize.height;
2711 0 : uchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2712 0 : uchannel->mStride = aData->mCbCrStride;
2713 0 : uchannel->mSkip = aData->mCbSkip;
2714 :
2715 0 : vchannel->mWidth = aData->mCbCrSize.width;
2716 0 : vchannel->mHeight = aData->mCbCrSize.height;
2717 0 : vchannel->mDataType = ChannelPixelLayoutDataType::Uint8;
2718 0 : vchannel->mStride = aData->mCbCrStride;
2719 0 : vchannel->mSkip = aData->mCrSkip;
2720 :
2721 0 : return layout;
2722 : }
2723 :
2724 : uint8_t
2725 0 : GetChannelCountOfImageFormat(ImageBitmapFormat aFormat)
2726 : {
2727 0 : UtilsUniquePtr format = Utils::GetUtils(aFormat);
2728 0 : MOZ_ASSERT(format, "Cannot get a valid ImageBitmapFormatUtils instance.");
2729 :
2730 0 : return format->GetChannelCount();
2731 : }
2732 :
2733 : uint32_t
2734 0 : CalculateImageBufferSize(ImageBitmapFormat aFormat,
2735 : uint32_t aWidth, uint32_t aHeight)
2736 : {
2737 0 : UtilsUniquePtr format = Utils::GetUtils(aFormat);
2738 0 : MOZ_ASSERT(format, "Cannot get a valid ImageBitmapFormatUtils instance.");
2739 :
2740 0 : return format->NeededBufferSize(aWidth, aHeight);
2741 : }
2742 :
2743 : UniquePtr<ImagePixelLayout>
2744 0 : CopyAndConvertImageData(ImageBitmapFormat aSrcFormat,
2745 : const uint8_t* aSrcBuffer,
2746 : const ImagePixelLayout* aSrcLayout,
2747 : ImageBitmapFormat aDstFormat,
2748 : uint8_t* aDstBuffer)
2749 : {
2750 0 : MOZ_ASSERT(aSrcBuffer, "Convert color from a null buffer.");
2751 0 : MOZ_ASSERT(aSrcLayout, "Convert color from a null layout.");
2752 0 : MOZ_ASSERT(aDstBuffer, "Convert color to a null buffer.");
2753 :
2754 0 : UtilsUniquePtr srcFormat = Utils::GetUtils(aSrcFormat);
2755 0 : UtilsUniquePtr dstFormat = Utils::GetUtils(aDstFormat);
2756 0 : MOZ_ASSERT(srcFormat, "Cannot get a valid ImageBitmapFormatUtils instance.");
2757 0 : MOZ_ASSERT(dstFormat, "Cannot get a valid ImageBitmapFormatUtils instance.");
2758 :
2759 0 : return srcFormat->ConvertTo(dstFormat.get(), aSrcBuffer, aSrcLayout, aDstBuffer);
2760 : }
2761 :
2762 : ImageBitmapFormat
2763 0 : FindBestMatchingFromat(ImageBitmapFormat aSrcFormat,
2764 : const Sequence<ImageBitmapFormat>& aCandidates) {
2765 :
2766 0 : for(auto& candidate : aCandidates) {
2767 0 : UtilsUniquePtr candidateFormat = Utils::GetUtils(candidate);
2768 0 : MOZ_ASSERT(candidateFormat, "Cannot get a valid ImageBitmapFormatUtils instance.");
2769 :
2770 0 : if (candidateFormat->CanConvertFrom(aSrcFormat)) {
2771 0 : return candidate;
2772 : }
2773 : }
2774 :
2775 0 : return ImageBitmapFormat::EndGuard_;
2776 : }
2777 :
2778 : } // namespace dom
2779 : } // namespace mozilla
|