2 * Copyright (C) 2010 Apple Inc. All rights reserved.
3 * Copyright (C) 2010 Google Inc. All rights reserved.
4 * Copyright (C) 2010 Mozilla Corporation. All rights reserved.
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
15 * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
16 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
18 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
19 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
20 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
21 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
22 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
23 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 #ifndef WEBGLTEXELCONVERSIONS_H_
29 #define WEBGLTEXELCONVERSIONS_H_
35 #include "WebGLTypes.h"
37 #include "mozilla/Attributes.h"
41 // single precision float
42 // seeeeeeeemmmmmmmmmmmmmmmmmmmmmmm
44 // half precision float
47 // IEEE 16bits floating point:
48 const uint16_t kFloat16Value_Zero
= 0x0000; // = 0000000000000000b
49 const uint16_t kFloat16Value_One
= 0x3C00; // = 0011110000000000b
50 const uint16_t kFloat16Value_Infinity
= 0x7C00; // = 0111110000000000b
51 const uint16_t kFloat16Value_NaN
= 0x7FFF; // = 011111yyyyyyyyyyb (nonzero y)
53 MOZ_ALWAYS_INLINE
uint16_t
54 packToFloat16(float v
)
63 // pull the sign from v into f16bits
64 uint16_t f16Bits
= uint16_t(f32Bits
>> 16) & 0x8000;
65 const uint32_t mantissa
= f32Bits
& 0x7FFFFF;
66 const uint32_t exp
= (f32Bits
>> 23) & 0xFF;
68 // Adapted from: OpenGL ES 2.0 Programming Guide Appx.
69 // Converting Float to Half-Float
70 // 143 = 255 - 127 + 15
71 // = sp_max - sp_bias + hp_bias
73 if (mantissa
&& exp
== 0xFF) {
74 // Single precision was NaN
75 return f16Bits
| kFloat16Value_NaN
;
77 // Outside range, store as infinity
78 return f16Bits
| kFloat16Value_Infinity
;
82 // too small, try to make a denormalized number
83 // 112 = 255 - 127 - (15 + 1)
84 // = sp_max - sp_bias - (hp_bias + 1)
86 return f16Bits
| uint16_t(mantissa
>> (14 + 112 - exp
));
89 f16Bits
|= uint16_t(exp
- 112) << 10;
90 f16Bits
|= uint16_t(mantissa
>> 13) & 0x03FF;
95 MOZ_ALWAYS_INLINE
float
96 unpackFromFloat16(uint16_t v
)
104 f32Bits
= uint32_t(v
& 0x8000) << 16;
105 uint16_t exp
= (v
>> 10) & 0x001F;
106 uint16_t mantissa
= v
& 0x03FF;
109 // Handle denormalized numbers
110 // Adapted from: OpenGL ES 2.0 Programming Guide Appx.
111 // Converting Float to Half-Float
113 exp
= 112; // See packToFloat16
115 // For every leading zero, decrement the exponent
116 // and shift the mantissa to the left
117 while ((mantissa
& (1 << 10)) == 0) {
123 f32Bits
|= (exp
<< 23) | (mantissa
<< 13);
125 // Denormalized number
136 f32Bits
|= 0x7FFFFFFF;
138 // this is -inf or +inf
139 f32Bits
|= 0x7F800000;
144 f32Bits
|= uint32_t(exp
+ (-15 + 127)) << 23;
145 f32Bits
|= uint32_t(v
& 0x03FF) << 13;
150 MOZ_BEGIN_ENUM_CLASS(WebGLTexelPremultiplicationOp
, int)
154 MOZ_END_ENUM_CLASS(WebGLTexelPremultiplicationOp
)
156 namespace WebGLTexelConversions
{
158 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
161 static const bool Value
=
162 Format
== WebGLTexelFormat::RGBA32F
||
163 Format
== WebGLTexelFormat::RGB32F
||
164 Format
== WebGLTexelFormat::RA32F
||
165 Format
== WebGLTexelFormat::R32F
||
166 Format
== WebGLTexelFormat::A32F
;
169 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
170 struct IsHalfFloatFormat
172 static const bool Value
=
173 Format
== WebGLTexelFormat::RGBA16F
||
174 Format
== WebGLTexelFormat::RGB16F
||
175 Format
== WebGLTexelFormat::RA16F
||
176 Format
== WebGLTexelFormat::R16F
||
177 Format
== WebGLTexelFormat::A16F
;
180 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
183 static const bool Value
=
184 Format
== WebGLTexelFormat::RGBA4444
||
185 Format
== WebGLTexelFormat::RGBA5551
||
186 Format
== WebGLTexelFormat::RGB565
;
189 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
,
190 bool IsFloat
= IsFloatFormat
<Format
>::Value
,
191 bool Is16bpp
= Is16bppFormat
<Format
>::Value
,
192 bool IsHalfFloat
= IsHalfFloatFormat
<Format
>::Value
>
193 struct DataTypeForFormat
195 typedef uint8_t Type
;
198 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
199 struct DataTypeForFormat
<Format
, true, false, false>
204 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
205 struct DataTypeForFormat
<Format
, false, true, false>
207 typedef uint16_t Type
;
210 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
211 struct DataTypeForFormat
<Format
, false, false, true>
213 typedef uint16_t Type
;
216 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
>
217 struct IntermediateFormat
219 static const MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Value
220 = IsFloatFormat
<Format
>::Value
221 ? WebGLTexelFormat::RGBA32F
222 : IsHalfFloatFormat
<Format
>::Value
? WebGLTexelFormat::RGBA16F
223 : WebGLTexelFormat::RGBA8
;
227 GLFormatForTexelFormat(WebGLTexelFormat format
) {
229 case WebGLTexelFormat::R8
: return LOCAL_GL_LUMINANCE
;
230 case WebGLTexelFormat::A8
: return LOCAL_GL_ALPHA
;
231 case WebGLTexelFormat::RA8
: return LOCAL_GL_LUMINANCE_ALPHA
;
232 case WebGLTexelFormat::RGBA5551
: return LOCAL_GL_RGBA
;
233 case WebGLTexelFormat::RGBA4444
: return LOCAL_GL_RGBA
;
234 case WebGLTexelFormat::RGB565
: return LOCAL_GL_RGB
;
235 case WebGLTexelFormat::D16
: return LOCAL_GL_DEPTH_COMPONENT
;
236 case WebGLTexelFormat::RGB8
: return LOCAL_GL_RGB
;
237 case WebGLTexelFormat::RGBA8
: return LOCAL_GL_RGBA
;
238 case WebGLTexelFormat::BGRA8
: return LOCAL_GL_BGRA
;
239 case WebGLTexelFormat::BGRX8
: return LOCAL_GL_BGR
;
240 case WebGLTexelFormat::R32F
: return LOCAL_GL_LUMINANCE
;
241 case WebGLTexelFormat::A32F
: return LOCAL_GL_ALPHA
;
242 case WebGLTexelFormat::D32
: return LOCAL_GL_DEPTH_COMPONENT
;
243 case WebGLTexelFormat::D24S8
: return LOCAL_GL_DEPTH_STENCIL
;
244 case WebGLTexelFormat::RA32F
: return LOCAL_GL_LUMINANCE_ALPHA
;
245 case WebGLTexelFormat::RGB32F
: return LOCAL_GL_RGB
;
246 case WebGLTexelFormat::RGBA32F
: return LOCAL_GL_RGBA
;
247 case WebGLTexelFormat::R16F
: return LOCAL_GL_LUMINANCE
;
248 case WebGLTexelFormat::A16F
: return LOCAL_GL_ALPHA
;
249 case WebGLTexelFormat::RA16F
: return LOCAL_GL_LUMINANCE_ALPHA
;
250 case WebGLTexelFormat::RGB16F
: return LOCAL_GL_RGB
;
251 case WebGLTexelFormat::RGBA16F
: return LOCAL_GL_RGBA
;
253 MOZ_CRASH("Unknown texel format. Coding mistake?");
254 return LOCAL_GL_INVALID_ENUM
;
258 inline size_t TexelBytesForFormat(WebGLTexelFormat format
) {
260 case WebGLTexelFormat::R8
:
261 case WebGLTexelFormat::A8
:
263 case WebGLTexelFormat::RA8
:
264 case WebGLTexelFormat::RGBA5551
:
265 case WebGLTexelFormat::RGBA4444
:
266 case WebGLTexelFormat::RGB565
:
267 case WebGLTexelFormat::R16F
:
268 case WebGLTexelFormat::A16F
:
269 case WebGLTexelFormat::D16
:
271 case WebGLTexelFormat::RGB8
:
273 case WebGLTexelFormat::RGBA8
:
274 case WebGLTexelFormat::BGRA8
:
275 case WebGLTexelFormat::BGRX8
:
276 case WebGLTexelFormat::R32F
:
277 case WebGLTexelFormat::A32F
:
278 case WebGLTexelFormat::D32
:
279 case WebGLTexelFormat::D24S8
:
280 case WebGLTexelFormat::RA16F
:
282 case WebGLTexelFormat::RGB16F
:
284 case WebGLTexelFormat::RGBA16F
:
285 case WebGLTexelFormat::RA32F
:
287 case WebGLTexelFormat::RGB32F
:
289 case WebGLTexelFormat::RGBA32F
:
292 MOZ_ASSERT(false, "Unknown texel format. Coding mistake?");
297 MOZ_ALWAYS_INLINE
bool HasAlpha(WebGLTexelFormat format
) {
298 return format
== WebGLTexelFormat::A8
||
299 format
== WebGLTexelFormat::A16F
||
300 format
== WebGLTexelFormat::A32F
||
301 format
== WebGLTexelFormat::RA8
||
302 format
== WebGLTexelFormat::RA16F
||
303 format
== WebGLTexelFormat::RA32F
||
304 format
== WebGLTexelFormat::RGBA8
||
305 format
== WebGLTexelFormat::BGRA8
||
306 format
== WebGLTexelFormat::RGBA16F
||
307 format
== WebGLTexelFormat::RGBA32F
||
308 format
== WebGLTexelFormat::RGBA4444
||
309 format
== WebGLTexelFormat::RGBA5551
;
312 MOZ_ALWAYS_INLINE
bool HasColor(WebGLTexelFormat format
) {
313 return format
== WebGLTexelFormat::R8
||
314 format
== WebGLTexelFormat::R16F
||
315 format
== WebGLTexelFormat::R32F
||
316 format
== WebGLTexelFormat::RA8
||
317 format
== WebGLTexelFormat::RA16F
||
318 format
== WebGLTexelFormat::RA32F
||
319 format
== WebGLTexelFormat::RGB8
||
320 format
== WebGLTexelFormat::BGRX8
||
321 format
== WebGLTexelFormat::RGB565
||
322 format
== WebGLTexelFormat::RGB16F
||
323 format
== WebGLTexelFormat::RGB32F
||
324 format
== WebGLTexelFormat::RGBA8
||
325 format
== WebGLTexelFormat::BGRA8
||
326 format
== WebGLTexelFormat::RGBA16F
||
327 format
== WebGLTexelFormat::RGBA32F
||
328 format
== WebGLTexelFormat::RGBA4444
||
329 format
== WebGLTexelFormat::RGBA5551
;
333 /****** BEGIN CODE SHARED WITH WEBKIT ******/
335 // the pack/unpack functions here are originally from this file:
336 // http://trac.webkit.org/browser/trunk/WebCore/platform/graphics/GraphicsContext3D.cpp
338 //----------------------------------------------------------------------
339 // Pixel unpacking routines.
341 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
, typename SrcType
, typename DstType
>
342 MOZ_ALWAYS_INLINE
void
343 unpack(const SrcType
* __restrict src
,
344 DstType
* __restrict dst
)
346 MOZ_ASSERT(false, "Unimplemented texture format conversion");
349 template<> MOZ_ALWAYS_INLINE
void
350 unpack
<WebGLTexelFormat::RGBA8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
358 template<> MOZ_ALWAYS_INLINE
void
359 unpack
<WebGLTexelFormat::RGB8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
367 template<> MOZ_ALWAYS_INLINE
void
368 unpack
<WebGLTexelFormat::BGRA8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
376 template<> MOZ_ALWAYS_INLINE
void
377 unpack
<WebGLTexelFormat::BGRX8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
385 template<> MOZ_ALWAYS_INLINE
void
386 unpack
<WebGLTexelFormat::RGBA5551
, uint16_t, uint8_t>(const uint16_t* __restrict src
, uint8_t* __restrict dst
)
388 uint16_t packedValue
= src
[0];
389 uint8_t r
= (packedValue
>> 11) & 0x1F;
390 uint8_t g
= (packedValue
>> 6) & 0x1F;
391 uint8_t b
= (packedValue
>> 1) & 0x1F;
392 dst
[0] = (r
<< 3) | (r
& 0x7);
393 dst
[1] = (g
<< 3) | (g
& 0x7);
394 dst
[2] = (b
<< 3) | (b
& 0x7);
395 dst
[3] = (packedValue
& 0x1) ? 0xFF : 0;
398 template<> MOZ_ALWAYS_INLINE
void
399 unpack
<WebGLTexelFormat::RGBA4444
, uint16_t, uint8_t>(const uint16_t* __restrict src
, uint8_t* __restrict dst
)
401 uint16_t packedValue
= src
[0];
402 uint8_t r
= (packedValue
>> 12) & 0x0F;
403 uint8_t g
= (packedValue
>> 8) & 0x0F;
404 uint8_t b
= (packedValue
>> 4) & 0x0F;
405 uint8_t a
= packedValue
& 0x0F;
406 dst
[0] = (r
<< 4) | r
;
407 dst
[1] = (g
<< 4) | g
;
408 dst
[2] = (b
<< 4) | b
;
409 dst
[3] = (a
<< 4) | a
;
412 template<> MOZ_ALWAYS_INLINE
void
413 unpack
<WebGLTexelFormat::RGB565
, uint16_t, uint8_t>(const uint16_t* __restrict src
, uint8_t* __restrict dst
)
415 uint16_t packedValue
= src
[0];
416 uint8_t r
= (packedValue
>> 11) & 0x1F;
417 uint8_t g
= (packedValue
>> 5) & 0x3F;
418 uint8_t b
= packedValue
& 0x1F;
419 dst
[0] = (r
<< 3) | (r
& 0x7);
420 dst
[1] = (g
<< 2) | (g
& 0x3);
421 dst
[2] = (b
<< 3) | (b
& 0x7);
425 template<> MOZ_ALWAYS_INLINE
void
426 unpack
<WebGLTexelFormat::R8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
434 template<> MOZ_ALWAYS_INLINE
void
435 unpack
<WebGLTexelFormat::RA8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
443 template<> MOZ_ALWAYS_INLINE
void
444 unpack
<WebGLTexelFormat::A8
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
452 template<> MOZ_ALWAYS_INLINE
void
453 unpack
<WebGLTexelFormat::RGBA32F
, float, float>(const float* __restrict src
, float* __restrict dst
)
461 template<> MOZ_ALWAYS_INLINE
void
462 unpack
<WebGLTexelFormat::RGB32F
, float, float>(const float* __restrict src
, float* __restrict dst
)
470 template<> MOZ_ALWAYS_INLINE
void
471 unpack
<WebGLTexelFormat::R32F
, float, float>(const float* __restrict src
, float* __restrict dst
)
479 template<> MOZ_ALWAYS_INLINE
void
480 unpack
<WebGLTexelFormat::RA32F
, float, float>(const float* __restrict src
, float* __restrict dst
)
488 template<> MOZ_ALWAYS_INLINE
void
489 unpack
<WebGLTexelFormat::A32F
, float, float>(const float* __restrict src
, float* __restrict dst
)
497 template<> MOZ_ALWAYS_INLINE
void
498 unpack
<WebGLTexelFormat::RGBA16F
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
506 template<> MOZ_ALWAYS_INLINE
void
507 unpack
<WebGLTexelFormat::RGB16F
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
512 dst
[3] = kFloat16Value_One
;
515 template<> MOZ_ALWAYS_INLINE
void
516 unpack
<WebGLTexelFormat::R16F
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
521 dst
[3] = kFloat16Value_One
;
524 template<> MOZ_ALWAYS_INLINE
void
525 unpack
<WebGLTexelFormat::RA16F
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
533 template<> MOZ_ALWAYS_INLINE
void
534 unpack
<WebGLTexelFormat::A16F
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
536 dst
[0] = kFloat16Value_Zero
;
537 dst
[1] = kFloat16Value_Zero
;
538 dst
[2] = kFloat16Value_Zero
;
542 //----------------------------------------------------------------------
543 // Pixel packing routines.
546 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat
) Format
,
547 MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelPremultiplicationOp
) PremultiplicationOp
,
550 MOZ_ALWAYS_INLINE
void
551 pack(const SrcType
* __restrict src
,
552 DstType
* __restrict dst
)
554 MOZ_ASSERT(false, "Unimplemented texture format conversion");
557 template<> MOZ_ALWAYS_INLINE
void
558 pack
<WebGLTexelFormat::A8
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
563 template<> MOZ_ALWAYS_INLINE
void
564 pack
<WebGLTexelFormat::A8
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
569 template<> MOZ_ALWAYS_INLINE
void
570 pack
<WebGLTexelFormat::A8
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
575 template<> MOZ_ALWAYS_INLINE
void
576 pack
<WebGLTexelFormat::R8
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
581 template<> MOZ_ALWAYS_INLINE
void
582 pack
<WebGLTexelFormat::R8
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
584 float scaleFactor
= src
[3] / 255.0f
;
585 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
589 template<> MOZ_ALWAYS_INLINE
void
590 pack
<WebGLTexelFormat::R8
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
592 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
593 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
597 template<> MOZ_ALWAYS_INLINE
void
598 pack
<WebGLTexelFormat::RA8
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
604 template<> MOZ_ALWAYS_INLINE
void
605 pack
<WebGLTexelFormat::RA8
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
607 float scaleFactor
= src
[3] / 255.0f
;
608 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
613 // FIXME: this routine is lossy and must be removed.
614 template<> MOZ_ALWAYS_INLINE
void
615 pack
<WebGLTexelFormat::RA8
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
617 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
618 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
623 template<> MOZ_ALWAYS_INLINE
void
624 pack
<WebGLTexelFormat::RGB8
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
631 template<> MOZ_ALWAYS_INLINE
void
632 pack
<WebGLTexelFormat::RGB8
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
634 float scaleFactor
= src
[3] / 255.0f
;
635 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
636 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
637 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
643 template<> MOZ_ALWAYS_INLINE
void
644 pack
<WebGLTexelFormat::RGB8
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
646 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
647 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
648 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
649 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
655 template<> MOZ_ALWAYS_INLINE
void
656 pack
<WebGLTexelFormat::RGBA8
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
664 template<> MOZ_ALWAYS_INLINE
void
665 pack
<WebGLTexelFormat::RGBA8
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
667 float scaleFactor
= src
[3] / 255.0f
;
668 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
669 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
670 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
677 // FIXME: this routine is lossy and must be removed.
678 template<> MOZ_ALWAYS_INLINE
void
679 pack
<WebGLTexelFormat::RGBA8
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
681 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
682 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
683 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
684 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
691 template<> MOZ_ALWAYS_INLINE
void
692 pack
<WebGLTexelFormat::RGBA4444
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
694 *dst
= ( ((src
[0] & 0xF0) << 8)
695 | ((src
[1] & 0xF0) << 4)
700 template<> MOZ_ALWAYS_INLINE
void
701 pack
<WebGLTexelFormat::RGBA4444
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
703 float scaleFactor
= src
[3] / 255.0f
;
704 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
705 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
706 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
707 *dst
= ( ((srcR
& 0xF0) << 8)
708 | ((srcG
& 0xF0) << 4)
713 // FIXME: this routine is lossy and must be removed.
714 template<> MOZ_ALWAYS_INLINE
void
715 pack
<WebGLTexelFormat::RGBA4444
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
717 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
718 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
719 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
720 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
721 *dst
= ( ((srcR
& 0xF0) << 8)
722 | ((srcG
& 0xF0) << 4)
727 template<> MOZ_ALWAYS_INLINE
void
728 pack
<WebGLTexelFormat::RGBA5551
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
730 *dst
= ( ((src
[0] & 0xF8) << 8)
731 | ((src
[1] & 0xF8) << 3)
732 | ((src
[2] & 0xF8) >> 2)
736 template<> MOZ_ALWAYS_INLINE
void
737 pack
<WebGLTexelFormat::RGBA5551
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
739 float scaleFactor
= src
[3] / 255.0f
;
740 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
741 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
742 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
743 *dst
= ( ((srcR
& 0xF8) << 8)
744 | ((srcG
& 0xF8) << 3)
745 | ((srcB
& 0xF8) >> 2)
749 // FIXME: this routine is lossy and must be removed.
750 template<> MOZ_ALWAYS_INLINE
void
751 pack
<WebGLTexelFormat::RGBA5551
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
753 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
754 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
755 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
756 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
757 *dst
= ( ((srcR
& 0xF8) << 8)
758 | ((srcG
& 0xF8) << 3)
759 | ((srcB
& 0xF8) >> 2)
763 template<> MOZ_ALWAYS_INLINE
void
764 pack
<WebGLTexelFormat::RGB565
, WebGLTexelPremultiplicationOp::None
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
766 *dst
= ( ((src
[0] & 0xF8) << 8)
767 | ((src
[1] & 0xFC) << 3)
768 | ((src
[2] & 0xF8) >> 3));
771 template<> MOZ_ALWAYS_INLINE
void
772 pack
<WebGLTexelFormat::RGB565
, WebGLTexelPremultiplicationOp::Premultiply
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
774 float scaleFactor
= src
[3] / 255.0f
;
775 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
776 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
777 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
778 *dst
= ( ((srcR
& 0xF8) << 8)
779 | ((srcG
& 0xFC) << 3)
780 | ((srcB
& 0xF8) >> 3));
783 // FIXME: this routine is lossy and must be removed.
784 template<> MOZ_ALWAYS_INLINE
void
785 pack
<WebGLTexelFormat::RGB565
, WebGLTexelPremultiplicationOp::Unpremultiply
, uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
787 float scaleFactor
= src
[3] ? 255.0f
/ src
[3] : 1.0f
;
788 uint8_t srcR
= static_cast<uint8_t>(src
[0] * scaleFactor
);
789 uint8_t srcG
= static_cast<uint8_t>(src
[1] * scaleFactor
);
790 uint8_t srcB
= static_cast<uint8_t>(src
[2] * scaleFactor
);
791 *dst
= ( ((srcR
& 0xF8) << 8)
792 | ((srcG
& 0xFC) << 3)
793 | ((srcB
& 0xF8) >> 3));
796 template<> MOZ_ALWAYS_INLINE
void
797 pack
<WebGLTexelFormat::RGB32F
, WebGLTexelPremultiplicationOp::None
, float, float>(const float* __restrict src
, float* __restrict dst
)
804 template<> MOZ_ALWAYS_INLINE
void
805 pack
<WebGLTexelFormat::RGB32F
, WebGLTexelPremultiplicationOp::Premultiply
, float, float>(const float* __restrict src
, float* __restrict dst
)
807 float scaleFactor
= src
[3];
808 dst
[0] = src
[0] * scaleFactor
;
809 dst
[1] = src
[1] * scaleFactor
;
810 dst
[2] = src
[2] * scaleFactor
;
813 template<> MOZ_ALWAYS_INLINE
void
814 pack
<WebGLTexelFormat::RGBA32F
, WebGLTexelPremultiplicationOp::None
, float, float>(const float* __restrict src
, float* __restrict dst
)
822 template<> MOZ_ALWAYS_INLINE
void
823 pack
<WebGLTexelFormat::RGBA32F
, WebGLTexelPremultiplicationOp::Premultiply
, float, float>(const float* __restrict src
, float* __restrict dst
)
825 float scaleFactor
= src
[3];
826 dst
[0] = src
[0] * scaleFactor
;
827 dst
[1] = src
[1] * scaleFactor
;
828 dst
[2] = src
[2] * scaleFactor
;
832 template<> MOZ_ALWAYS_INLINE
void
833 pack
<WebGLTexelFormat::A32F
, WebGLTexelPremultiplicationOp::None
, float, float>(const float* __restrict src
, float* __restrict dst
)
838 template<> MOZ_ALWAYS_INLINE
void
839 pack
<WebGLTexelFormat::A32F
, WebGLTexelPremultiplicationOp::Premultiply
, float, float>(const float* __restrict src
, float* __restrict dst
)
844 template<> MOZ_ALWAYS_INLINE
void
845 pack
<WebGLTexelFormat::R32F
, WebGLTexelPremultiplicationOp::None
, float, float>(const float* __restrict src
, float* __restrict dst
)
850 template<> MOZ_ALWAYS_INLINE
void
851 pack
<WebGLTexelFormat::R32F
, WebGLTexelPremultiplicationOp::Premultiply
, float, float>(const float* __restrict src
, float* __restrict dst
)
853 float scaleFactor
= src
[3];
854 dst
[0] = src
[0] * scaleFactor
;
857 template<> MOZ_ALWAYS_INLINE
void
858 pack
<WebGLTexelFormat::RA32F
, WebGLTexelPremultiplicationOp::None
, float, float>(const float* __restrict src
, float* __restrict dst
)
864 template<> MOZ_ALWAYS_INLINE
void
865 pack
<WebGLTexelFormat::RA32F
, WebGLTexelPremultiplicationOp::Premultiply
, float, float>(const float* __restrict src
, float* __restrict dst
)
867 float scaleFactor
= src
[3];
868 dst
[0] = src
[0] * scaleFactor
;
869 dst
[1] = scaleFactor
;
872 template<> MOZ_ALWAYS_INLINE
void
873 pack
<WebGLTexelFormat::RGB16F
, WebGLTexelPremultiplicationOp::None
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
880 template<> MOZ_ALWAYS_INLINE
void
881 pack
<WebGLTexelFormat::RGB16F
, WebGLTexelPremultiplicationOp::Premultiply
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
883 float scaleFactor
= unpackFromFloat16(src
[3]);
884 dst
[0] = packToFloat16(unpackFromFloat16(src
[0]) * scaleFactor
);
885 dst
[1] = packToFloat16(unpackFromFloat16(src
[1]) * scaleFactor
);
886 dst
[2] = packToFloat16(unpackFromFloat16(src
[2]) * scaleFactor
);
889 template<> MOZ_ALWAYS_INLINE
void
890 pack
<WebGLTexelFormat::RGBA16F
, WebGLTexelPremultiplicationOp::None
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
898 template<> MOZ_ALWAYS_INLINE
void
899 pack
<WebGLTexelFormat::RGBA16F
, WebGLTexelPremultiplicationOp::Premultiply
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
901 float scaleFactor
= unpackFromFloat16(src
[3]);
902 dst
[0] = packToFloat16(unpackFromFloat16(src
[0]) * scaleFactor
);
903 dst
[1] = packToFloat16(unpackFromFloat16(src
[1]) * scaleFactor
);
904 dst
[2] = packToFloat16(unpackFromFloat16(src
[2]) * scaleFactor
);
908 template<> MOZ_ALWAYS_INLINE
void
909 pack
<WebGLTexelFormat::A16F
, WebGLTexelPremultiplicationOp::None
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
914 template<> MOZ_ALWAYS_INLINE
void
915 pack
<WebGLTexelFormat::A16F
, WebGLTexelPremultiplicationOp::Premultiply
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
920 template<> MOZ_ALWAYS_INLINE
void
921 pack
<WebGLTexelFormat::R16F
, WebGLTexelPremultiplicationOp::None
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
926 template<> MOZ_ALWAYS_INLINE
void
927 pack
<WebGLTexelFormat::R16F
, WebGLTexelPremultiplicationOp::Premultiply
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
929 float scaleFactor
= unpackFromFloat16(src
[3]);
930 dst
[0] = packToFloat16(unpackFromFloat16(src
[0]) * scaleFactor
);
933 template<> MOZ_ALWAYS_INLINE
void
934 pack
<WebGLTexelFormat::RA16F
, WebGLTexelPremultiplicationOp::None
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
940 template<> MOZ_ALWAYS_INLINE
void
941 pack
<WebGLTexelFormat::RA16F
, WebGLTexelPremultiplicationOp::Premultiply
, uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
943 float scaleFactor
= unpackFromFloat16(src
[3]);
944 dst
[0] = packToFloat16(unpackFromFloat16(src
[0]) * scaleFactor
);
945 dst
[1] = scaleFactor
;
948 /****** END CODE SHARED WITH WEBKIT ******/
950 template<typename SrcType
, typename DstType
> MOZ_ALWAYS_INLINE
void
951 convertType(const SrcType
* __restrict src
, DstType
* __restrict dst
)
953 MOZ_ASSERT(false, "Unimplemented texture format conversion");
956 template<> MOZ_ALWAYS_INLINE
void
957 convertType
<uint8_t, uint8_t>(const uint8_t* __restrict src
, uint8_t* __restrict dst
)
965 template<> MOZ_ALWAYS_INLINE
void
966 convertType
<uint16_t, uint16_t>(const uint16_t* __restrict src
, uint16_t* __restrict dst
)
974 template<> MOZ_ALWAYS_INLINE
void
975 convertType
<float, float>(const float* __restrict src
, float* __restrict dst
)
983 template<> MOZ_ALWAYS_INLINE
void
984 convertType
<uint8_t, float>(const uint8_t* __restrict src
, float* __restrict dst
)
986 const float scaleFactor
= 1.f
/ 255.0f
;
987 dst
[0] = src
[0] * scaleFactor
;
988 dst
[1] = src
[1] * scaleFactor
;
989 dst
[2] = src
[2] * scaleFactor
;
990 dst
[3] = src
[3] * scaleFactor
;
993 template<> MOZ_ALWAYS_INLINE
void
994 convertType
<uint8_t, uint16_t>(const uint8_t* __restrict src
, uint16_t* __restrict dst
)
996 const float scaleFactor
= 1.f
/ 255.0f
;
997 dst
[0] = packToFloat16(src
[0] * scaleFactor
);
998 dst
[1] = packToFloat16(src
[1] * scaleFactor
);
999 dst
[2] = packToFloat16(src
[2] * scaleFactor
);
1000 dst
[3] = packToFloat16(src
[3] * scaleFactor
);
1003 } // end namespace WebGLTexelConversions
1005 } // end namespace mozilla
1007 #endif // WEBGLTEXELCONVERSIONS_H_