Bumping gaia.json for 2 gaia revision(s) a=gaia-bump
[gecko.git] / dom / canvas / WebGLTexelConversions.h
blobb654af9becf06d22519456c31282cdfa6d34f255
1 /*
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
8 * are met:
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_
31 #ifdef __SUNPRO_CC
32 #define __restrict
33 #endif
35 #include "WebGLTypes.h"
36 #include <stdint.h>
37 #include "mozilla/Attributes.h"
39 namespace mozilla {
41 // single precision float
42 // seeeeeeeemmmmmmmmmmmmmmmmmmmmmmm
44 // half precision float
45 // seeeeemmmmmmmmmm
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)
56 union {
57 float f32Value;
58 uint32_t f32Bits;
61 f32Value = 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
72 if (exp >= 143) {
73 if (mantissa && exp == 0xFF) {
74 // Single precision was NaN
75 return f16Bits | kFloat16Value_NaN;
76 } else {
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)
85 if (exp <= 112) {
86 return f16Bits | uint16_t(mantissa >> (14 + 112 - exp));
89 f16Bits |= uint16_t(exp - 112) << 10;
90 f16Bits |= uint16_t(mantissa >> 13) & 0x03FF;
92 return f16Bits;
95 MOZ_ALWAYS_INLINE float
96 unpackFromFloat16(uint16_t v)
98 union {
99 float f32Value;
100 uint32_t f32Bits;
103 // grab sign bit
104 f32Bits = uint32_t(v & 0x8000) << 16;
105 uint16_t exp = (v >> 10) & 0x001F;
106 uint16_t mantissa = v & 0x03FF;
108 if (exp) {
109 // Handle denormalized numbers
110 // Adapted from: OpenGL ES 2.0 Programming Guide Appx.
111 // Converting Float to Half-Float
112 if (mantissa) {
113 exp = 112; // See packToFloat16
114 mantissa <<= 1;
115 // For every leading zero, decrement the exponent
116 // and shift the mantissa to the left
117 while ((mantissa & (1 << 10)) == 0) {
118 mantissa <<= 1;
119 --exp;
121 mantissa &= 0x03FF;
123 f32Bits |= (exp << 23) | (mantissa << 13);
125 // Denormalized number
126 return f32Value;
129 // +/- zero
130 return f32Value;
133 if (exp == 0x001F) {
134 if (v & 0x03FF) {
135 // this is a NaN
136 f32Bits |= 0x7FFFFFFF;
137 } else {
138 // this is -inf or +inf
139 f32Bits |= 0x7F800000;
141 return f32Value;
144 f32Bits |= uint32_t(exp + (-15 + 127)) << 23;
145 f32Bits |= uint32_t(v & 0x03FF) << 13;
147 return f32Value;
150 MOZ_BEGIN_ENUM_CLASS(WebGLTexelPremultiplicationOp, int)
151 None,
152 Premultiply,
153 Unpremultiply
154 MOZ_END_ENUM_CLASS(WebGLTexelPremultiplicationOp)
156 namespace WebGLTexelConversions {
158 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat) Format>
159 struct IsFloatFormat
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>
181 struct Is16bppFormat
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>
201 typedef float Type;
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;
226 inline GLenum
227 GLFormatForTexelFormat(WebGLTexelFormat format) {
228 switch (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;
252 default:
253 MOZ_CRASH("Unknown texel format. Coding mistake?");
254 return LOCAL_GL_INVALID_ENUM;
258 inline size_t TexelBytesForFormat(WebGLTexelFormat format) {
259 switch (format) {
260 case WebGLTexelFormat::R8:
261 case WebGLTexelFormat::A8:
262 return 1;
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:
270 return 2;
271 case WebGLTexelFormat::RGB8:
272 return 3;
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:
281 return 4;
282 case WebGLTexelFormat::RGB16F:
283 return 6;
284 case WebGLTexelFormat::RGBA16F:
285 case WebGLTexelFormat::RA32F:
286 return 8;
287 case WebGLTexelFormat::RGB32F:
288 return 12;
289 case WebGLTexelFormat::RGBA32F:
290 return 16;
291 default:
292 MOZ_ASSERT(false, "Unknown texel format. Coding mistake?");
293 return 0;
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)
352 dst[0] = src[0];
353 dst[1] = src[1];
354 dst[2] = src[2];
355 dst[3] = src[3];
358 template<> MOZ_ALWAYS_INLINE void
359 unpack<WebGLTexelFormat::RGB8, uint8_t, uint8_t>(const uint8_t* __restrict src, uint8_t* __restrict dst)
361 dst[0] = src[0];
362 dst[1] = src[1];
363 dst[2] = src[2];
364 dst[3] = 0xFF;
367 template<> MOZ_ALWAYS_INLINE void
368 unpack<WebGLTexelFormat::BGRA8, uint8_t, uint8_t>(const uint8_t* __restrict src, uint8_t* __restrict dst)
370 dst[0] = src[2];
371 dst[1] = src[1];
372 dst[2] = src[0];
373 dst[3] = src[3];
376 template<> MOZ_ALWAYS_INLINE void
377 unpack<WebGLTexelFormat::BGRX8, uint8_t, uint8_t>(const uint8_t* __restrict src, uint8_t* __restrict dst)
379 dst[0] = src[2];
380 dst[1] = src[1];
381 dst[2] = src[0];
382 dst[3] = 0xFF;
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);
422 dst[3] = 0xFF;
425 template<> MOZ_ALWAYS_INLINE void
426 unpack<WebGLTexelFormat::R8, uint8_t, uint8_t>(const uint8_t* __restrict src, uint8_t* __restrict dst)
428 dst[0] = src[0];
429 dst[1] = src[0];
430 dst[2] = src[0];
431 dst[3] = 0xFF;
434 template<> MOZ_ALWAYS_INLINE void
435 unpack<WebGLTexelFormat::RA8, uint8_t, uint8_t>(const uint8_t* __restrict src, uint8_t* __restrict dst)
437 dst[0] = src[0];
438 dst[1] = src[0];
439 dst[2] = src[0];
440 dst[3] = src[1];
443 template<> MOZ_ALWAYS_INLINE void
444 unpack<WebGLTexelFormat::A8, uint8_t, uint8_t>(const uint8_t* __restrict src, uint8_t* __restrict dst)
446 dst[0] = 0;
447 dst[1] = 0;
448 dst[2] = 0;
449 dst[3] = src[0];
452 template<> MOZ_ALWAYS_INLINE void
453 unpack<WebGLTexelFormat::RGBA32F, float, float>(const float* __restrict src, float* __restrict dst)
455 dst[0] = src[0];
456 dst[1] = src[1];
457 dst[2] = src[2];
458 dst[3] = src[3];
461 template<> MOZ_ALWAYS_INLINE void
462 unpack<WebGLTexelFormat::RGB32F, float, float>(const float* __restrict src, float* __restrict dst)
464 dst[0] = src[0];
465 dst[1] = src[1];
466 dst[2] = src[2];
467 dst[3] = 1.0f;
470 template<> MOZ_ALWAYS_INLINE void
471 unpack<WebGLTexelFormat::R32F, float, float>(const float* __restrict src, float* __restrict dst)
473 dst[0] = src[0];
474 dst[1] = src[0];
475 dst[2] = src[0];
476 dst[3] = 1.0f;
479 template<> MOZ_ALWAYS_INLINE void
480 unpack<WebGLTexelFormat::RA32F, float, float>(const float* __restrict src, float* __restrict dst)
482 dst[0] = src[0];
483 dst[1] = src[0];
484 dst[2] = src[0];
485 dst[3] = src[1];
488 template<> MOZ_ALWAYS_INLINE void
489 unpack<WebGLTexelFormat::A32F, float, float>(const float* __restrict src, float* __restrict dst)
491 dst[0] = 0;
492 dst[1] = 0;
493 dst[2] = 0;
494 dst[3] = src[0];
497 template<> MOZ_ALWAYS_INLINE void
498 unpack<WebGLTexelFormat::RGBA16F, uint16_t, uint16_t>(const uint16_t* __restrict src, uint16_t* __restrict dst)
500 dst[0] = src[0];
501 dst[1] = src[1];
502 dst[2] = src[2];
503 dst[3] = src[3];
506 template<> MOZ_ALWAYS_INLINE void
507 unpack<WebGLTexelFormat::RGB16F, uint16_t, uint16_t>(const uint16_t* __restrict src, uint16_t* __restrict dst)
509 dst[0] = src[0];
510 dst[1] = src[1];
511 dst[2] = src[2];
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)
518 dst[0] = src[0];
519 dst[1] = src[0];
520 dst[2] = src[0];
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)
527 dst[0] = src[0];
528 dst[1] = src[0];
529 dst[2] = src[0];
530 dst[3] = src[1];
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;
539 dst[3] = src[0];
542 //----------------------------------------------------------------------
543 // Pixel packing routines.
546 template<MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelFormat) Format,
547 MOZ_ENUM_CLASS_ENUM_TYPE(WebGLTexelPremultiplicationOp) PremultiplicationOp,
548 typename SrcType,
549 typename DstType>
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)
560 dst[0] = src[3];
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)
566 dst[0] = src[3];
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)
572 dst[0] = src[3];
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)
578 dst[0] = src[0];
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);
586 dst[0] = srcR;
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);
594 dst[0] = srcR;
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)
600 dst[0] = src[0];
601 dst[1] = src[3];
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);
609 dst[0] = srcR;
610 dst[1] = src[3];
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);
619 dst[0] = srcR;
620 dst[1] = src[3];
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)
626 dst[0] = src[0];
627 dst[1] = src[1];
628 dst[2] = src[2];
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);
638 dst[0] = srcR;
639 dst[1] = srcG;
640 dst[2] = srcB;
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);
650 dst[0] = srcR;
651 dst[1] = srcG;
652 dst[2] = srcB;
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)
658 dst[0] = src[0];
659 dst[1] = src[1];
660 dst[2] = src[2];
661 dst[3] = src[3];
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);
671 dst[0] = srcR;
672 dst[1] = srcG;
673 dst[2] = srcB;
674 dst[3] = src[3];
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);
685 dst[0] = srcR;
686 dst[1] = srcG;
687 dst[2] = srcB;
688 dst[3] = src[3];
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)
696 | (src[2] & 0xF0)
697 | (src[3] >> 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)
709 | (srcB & 0xF0)
710 | (src[3] >> 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)
723 | (srcB & 0xF0)
724 | (src[3] >> 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)
733 | (src[3] >> 7));
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)
746 | (src[3] >> 7));
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)
760 | (src[3] >> 7));
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)
799 dst[0] = src[0];
800 dst[1] = src[1];
801 dst[2] = src[2];
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)
816 dst[0] = src[0];
817 dst[1] = src[1];
818 dst[2] = src[2];
819 dst[3] = src[3];
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;
829 dst[3] = src[3];
832 template<> MOZ_ALWAYS_INLINE void
833 pack<WebGLTexelFormat::A32F, WebGLTexelPremultiplicationOp::None, float, float>(const float* __restrict src, float* __restrict dst)
835 dst[0] = src[3];
838 template<> MOZ_ALWAYS_INLINE void
839 pack<WebGLTexelFormat::A32F, WebGLTexelPremultiplicationOp::Premultiply, float, float>(const float* __restrict src, float* __restrict dst)
841 dst[0] = src[3];
844 template<> MOZ_ALWAYS_INLINE void
845 pack<WebGLTexelFormat::R32F, WebGLTexelPremultiplicationOp::None, float, float>(const float* __restrict src, float* __restrict dst)
847 dst[0] = src[0];
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)
860 dst[0] = src[0];
861 dst[1] = src[3];
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)
875 dst[0] = src[0];
876 dst[1] = src[1];
877 dst[2] = src[2];
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)
892 dst[0] = src[0];
893 dst[1] = src[1];
894 dst[2] = src[2];
895 dst[3] = src[3];
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);
905 dst[3] = src[3];
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)
911 dst[0] = src[3];
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)
917 dst[0] = src[3];
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)
923 dst[0] = src[0];
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)
936 dst[0] = src[0];
937 dst[1] = src[3];
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)
959 dst[0] = src[0];
960 dst[1] = src[1];
961 dst[2] = src[2];
962 dst[3] = src[3];
965 template<> MOZ_ALWAYS_INLINE void
966 convertType<uint16_t, uint16_t>(const uint16_t* __restrict src, uint16_t* __restrict dst)
968 dst[0] = src[0];
969 dst[1] = src[1];
970 dst[2] = src[2];
971 dst[3] = src[3];
974 template<> MOZ_ALWAYS_INLINE void
975 convertType<float, float>(const float* __restrict src, float* __restrict dst)
977 dst[0] = src[0];
978 dst[1] = src[1];
979 dst[2] = src[2];
980 dst[3] = src[3];
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_