ScummVM API documentation
pixelformat.h
1/* ScummVM - Graphic Adventure Engine
2 *
3 * ScummVM is the legal property of its developers, whose names
4 * are too numerous to list here. Please refer to the COPYRIGHT
5 * file distributed with this source distribution.
6 *
7 * This program is free software: you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation, either version 3 of the License, or
10 * (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program. If not, see <http://www.gnu.org/licenses/>.
19 *
20 */
21
22#ifndef GRAPHICS_PIXELFORMAT_H
23#define GRAPHICS_PIXELFORMAT_H
24
25#include "common/scummsys.h"
26#include "common/str.h"
27
28#include "graphics/colormasks.h"
29
30namespace Graphics {
31
42template<int depth>
44};
46template<>
47struct ColorComponent<0> {
48 static inline uint expand(uint value) {
49 return 0;
50 }
51};
53template<>
54struct ColorComponent<1> {
55 static inline uint expand(uint value) {
56 return value ? 0xff : 0;
57 }
58};
60template<>
61struct ColorComponent<2> {
62 static inline uint expand(uint value) {
63 value &= 3;
64 return value |
65 (value << 2) |
66 (value << 4) |
67 (value << 6);
68 }
69};
71template<>
72struct ColorComponent<3> {
73 static inline uint expand(uint value) {
74 value &= 7;
75 return (value << 5) |
76 (value << 2) |
77 (value >> 1);
78 }
79};
81template<>
82struct ColorComponent<4> {
83 static inline uint expand(uint value) {
84 value &= 15;
85 return value |
86 (value << 4);
87 }
88};
90template<>
91struct ColorComponent<5> {
92 static inline uint expand(uint value) {
93 value &= 31;
94 return (value << 3) |
95 (value >> 2);
96 }
97};
99template<>
100struct ColorComponent<6> {
101 static inline uint expand(uint value) {
102 value &= 63;
103 return (value << 2) |
104 (value >> 4);
105 }
106};
108template<>
109struct ColorComponent<7> {
110 static inline uint expand(uint value) {
111 value &= 127;
112 return (value << 1) |
113 (value >> 6);
114 }
115};
117template<>
118struct ColorComponent<8> {
119 static inline uint expand(uint value) {
120 return value & 255;
121 }
122};
123
141 byte rLoss, gLoss, bLoss, aLoss;
142 byte rShift, gShift, bShift, aShift;
145 constexpr PixelFormat() :
146 bytesPerPixel(0),
147 rLoss(0), gLoss(0), bLoss(0), aLoss(0),
148 rShift(0), gShift(0), bShift(0), aShift(0) {}
149
168 constexpr PixelFormat(byte BytesPerPixel,
169 byte RBits, byte GBits, byte BBits, byte ABits,
170 byte RShift, byte GShift, byte BShift, byte AShift) :
171 bytesPerPixel(BytesPerPixel),
172 rLoss(8 - RBits),
173 gLoss(8 - GBits),
174 bLoss(8 - BBits),
175 aLoss(8 - ABits),
176 rShift((RBits == 0) ? 0 : RShift),
177 gShift((GBits == 0) ? 0 : GShift),
178 bShift((BBits == 0) ? 0 : BShift),
179 aShift((ABits == 0) ? 0 : AShift)
180 {
181 }
182
184 static constexpr inline PixelFormat createFormatCLUT8() {
185 return PixelFormat(1, 0, 0, 0, 0, 0, 0, 0, 0);
186 }
187
189 static constexpr inline PixelFormat createFormatRGB24() {
190#ifdef SCUMM_BIG_ENDIAN
191 return Graphics::PixelFormat(3, 8, 8, 8, 0, 16, 8, 0, 0);
192#else
193 return Graphics::PixelFormat(3, 8, 8, 8, 0, 0, 8, 16, 0);
194#endif
195 }
196
198 static constexpr inline PixelFormat createFormatBGR24() {
199#ifdef SCUMM_BIG_ENDIAN
200 return Graphics::PixelFormat(3, 8, 8, 8, 0, 0, 8, 16, 0);
201#else
202 return Graphics::PixelFormat(3, 8, 8, 8, 0, 16, 8, 0, 0);
203#endif
204 }
205
207 static constexpr inline PixelFormat createFormatRGBA32(bool alpha = true) {
208#ifdef SCUMM_BIG_ENDIAN
209 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 24, 16, 8, 0);
210#else
211 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 0, 8, 16, 24);
212#endif
213 }
214
216 static constexpr inline PixelFormat createFormatBGRA32(bool alpha = true) {
217#ifdef SCUMM_BIG_ENDIAN
218 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 8, 16, 24, 0);
219#else
220 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 16, 8, 0, 24);
221#endif
222 }
223
225 static constexpr inline PixelFormat createFormatABGR32(bool alpha = true) {
226#ifdef SCUMM_BIG_ENDIAN
227 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 0, 8, 16, 24);
228#else
229 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 24, 16, 8, 0);
230#endif
231 }
232
234 static constexpr inline PixelFormat createFormatARGB32(bool alpha = true) {
235#ifdef SCUMM_BIG_ENDIAN
236 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 16, 8, 0, 24);
237#else
238 return Graphics::PixelFormat(4, 8, 8, 8, alpha ? 8 : 0, 8, 16, 24, 0);
239#endif
240 }
241
243 inline bool operator==(const PixelFormat &fmt) const {
244 return bytesPerPixel == fmt.bytesPerPixel &&
245 rLoss == fmt.rLoss &&
246 gLoss == fmt.gLoss &&
247 bLoss == fmt.bLoss &&
248 aLoss == fmt.aLoss &&
249 rShift == fmt.rShift &&
250 gShift == fmt.gShift &&
251 bShift == fmt.bShift &&
252 aShift == fmt.aShift;
253 }
254
256 inline bool operator!=(const PixelFormat &fmt) const {
257 return !(*this == fmt);
258 }
259
261 inline uint32 RGBToColor(uint8 r, uint8 g, uint8 b) const {
262 return
263 ((0xFF >> aLoss) << aShift) |
264 (( r >> rLoss) << rShift) |
265 (( g >> gLoss) << gShift) |
266 (( b >> bLoss) << bShift);
267 }
268
269 template<class T>
270 inline uint32 RGBToColorT(uint8 r, uint8 g, uint8 b) const {
271 return T::kAlphaMask |
272 (((r << T::kRedShift) >> (8 - T::kRedBits)) & T::kRedMask) |
273 (((g << T::kGreenShift) >> (8 - T::kGreenBits)) & T::kGreenMask) |
274 (((b << T::kBlueShift) >> (8 - T::kBlueBits)) & T::kBlueMask);
275 }
276
278 inline uint32 ARGBToColor(uint8 a, uint8 r, uint8 g, uint8 b) const {
279 return
280 ((a >> aLoss) << aShift) |
281 ((r >> rLoss) << rShift) |
282 ((g >> gLoss) << gShift) |
283 ((b >> bLoss) << bShift);
284 }
285
286 template<class T>
287 inline uint32 ARGBToColorT(uint8 a, uint8 r, uint8 g, uint8 b) const {
288 return (((a << T::kAlphaShift) >> (8 - T::kAlphaBits)) & T::kAlphaMask) |
289 (((r << T::kRedShift) >> (8 - T::kRedBits)) & T::kRedMask) |
290 (((g << T::kGreenShift) >> (8 - T::kGreenBits)) & T::kGreenMask) |
291 (((b << T::kBlueShift) >> (8 - T::kBlueBits)) & T::kBlueMask);
292 }
293
295 inline void colorToRGB(uint32 color, uint8 &r, uint8 &g, uint8 &b) const {
296 r = expand(rBits(), color >> rShift);
297 g = expand(gBits(), color >> gShift);
298 b = expand(bBits(), color >> bShift);
299 }
300
301 template<class T>
302 inline void colorToRGBT(uint32 color, uint8 &r, uint8 &g, uint8 &b) const {
303 r = ((color & T::kRedMask) >> T::kRedShift) << (8 - T::kRedBits);
304 g = ((color & T::kGreenMask) >> T::kGreenShift) << (8 - T::kGreenBits);
305 b = ((color & T::kBlueMask) >> T::kBlueShift) << (8 - T::kBlueBits);
306 }
307
309 inline void colorToARGB(uint32 color, uint8 &a, uint8 &r, uint8 &g, uint8 &b) const {
310 a = (aBits() == 0) ? 0xFF : expand(aBits(), color >> aShift);
311 r = expand(rBits(), color >> rShift);
312 g = expand(gBits(), color >> gShift);
313 b = expand(bBits(), color >> bShift);
314 }
315
316 template<class T>
317 inline void colorToARGBT(uint32 color, uint8 &a, uint8 &r, uint8 &g, uint8 &b) const {
318 a = ((color & T::kAlphaMask) >> T::kAlphaShift) << (8 - T::kAlphaBits);
319 r = ((color & T::kRedMask) >> T::kRedShift) << (8 - T::kRedBits);
320 g = ((color & T::kGreenMask) >> T::kGreenShift) << (8 - T::kGreenBits);
321 b = ((color & T::kBlueMask) >> T::kBlueShift) << (8 - T::kBlueBits);
322 }
323
332 inline byte rBits() const {
333 return (8 - rLoss);
334 }
335
339 inline byte gBits() const {
340 return (8 - gLoss);
341 }
342
346 inline byte bBits() const {
347 return (8 - bLoss);
348 }
349
353 inline byte aBits() const {
354 return (8 - aLoss);
355 }
356
360 inline byte bpp() const {
361 return rBits() + gBits() + bBits() + aBits();
362 }
373 inline uint rMax() const {
374 return (1 << rBits()) - 1;
375 }
376
380 inline uint gMax() const {
381 return (1 << gBits()) - 1;
382 }
383
387 inline uint bMax() const {
388 return (1 << bBits()) - 1;
389 }
390
394 inline uint aMax() const {
395 return (1 << aBits()) - 1;
396 }
399 static inline uint expand(uint bits, uint color) {
400 switch (bits) {
401 case 0:
402 return ColorComponent<0>::expand(color);
403 case 1:
404 return ColorComponent<1>::expand(color);
405 case 2:
406 return ColorComponent<2>::expand(color);
407 case 3:
408 return ColorComponent<3>::expand(color);
409 case 4:
410 return ColorComponent<4>::expand(color);
411 case 5:
412 return ColorComponent<5>::expand(color);
413 case 6:
414 return ColorComponent<6>::expand(color);
415 case 7:
416 return ColorComponent<7>::expand(color);
417 case 8:
418 return ColorComponent<8>::expand(color);
419 default:
420 break;
421 }
422
423 // Unsupported
424 return 0;
425 }
428
430 bool isCLUT8() const {
431 // We do not really need to check masks when all shifts equal zeroes
432 return bytesPerPixel == 1 && rShift == 0 && gShift == 0 && bShift == 0 && aShift == 0;
433 }
434};
435
436template<>
437inline uint32 PixelFormat::RGBToColorT<ColorMasks<0> >(uint8 r, uint8 g, uint8 b) const {
438 return RGBToColor(r, g, b);
439}
440
441template<>
442inline uint32 PixelFormat::ARGBToColorT<ColorMasks<0> >(uint8 a, uint8 r, uint8 g, uint8 b) const {
443 return ARGBToColor(a, r, g, b);
444}
445
446template<>
447inline void PixelFormat::colorToRGBT<ColorMasks<0> >(uint32 color, uint8 &r, uint8 &g, uint8 &b) const {
448 colorToRGB(color, r, g, b);
449}
450
451template<>
452inline void PixelFormat::colorToARGBT<ColorMasks<0> >(uint32 color, uint8 &a, uint8 &r, uint8 &g, uint8 &b) const {
453 colorToARGB(color, a, r, g, b);
454}
455
460template<int bitFormat>
462 PixelFormat format;
463
464 format.bytesPerPixel = ColorMasks<bitFormat>::kBytesPerPixel;
465
466 format.rLoss = 8 - ColorMasks<bitFormat>::kRedBits;
467 format.gLoss = 8 - ColorMasks<bitFormat>::kGreenBits;
468 format.bLoss = 8 - ColorMasks<bitFormat>::kBlueBits;
469 format.aLoss = 8 - ColorMasks<bitFormat>::kAlphaBits;
470
471 format.rShift = ColorMasks<bitFormat>::kRedShift;
473 format.bShift = ColorMasks<bitFormat>::kBlueShift;
475
476 return format;
477}
478
479
481} // End of namespace Graphics
482
483#endif
Definition: str.h:59
PixelFormat createPixelFormat()
Definition: pixelformat.h:461
Definition: formatinfo.h:28
Definition: pixelformat.h:43
Definition: colormasks.h:30
Definition: pixelformat.h:138
byte bpp() const
Definition: pixelformat.h:360
byte aLoss
Definition: pixelformat.h:141
constexpr PixelFormat()
Definition: pixelformat.h:145
constexpr PixelFormat(byte BytesPerPixel, byte RBits, byte GBits, byte BBits, byte ABits, byte RShift, byte GShift, byte BShift, byte AShift)
Definition: pixelformat.h:168
static constexpr PixelFormat createFormatABGR32(bool alpha=true)
Definition: pixelformat.h:225
byte rBits() const
Definition: pixelformat.h:332
void colorToRGB(uint32 color, uint8 &r, uint8 &g, uint8 &b) const
Definition: pixelformat.h:295
bool operator==(const PixelFormat &fmt) const
Definition: pixelformat.h:243
uint32 RGBToColor(uint8 r, uint8 g, uint8 b) const
Definition: pixelformat.h:261
static constexpr PixelFormat createFormatRGBA32(bool alpha=true)
Definition: pixelformat.h:207
static uint expand(uint bits, uint color)
Definition: pixelformat.h:399
uint32 ARGBToColor(uint8 a, uint8 r, uint8 g, uint8 b) const
Definition: pixelformat.h:278
bool operator!=(const PixelFormat &fmt) const
Definition: pixelformat.h:256
bool isCLUT8() const
Definition: pixelformat.h:430
static constexpr PixelFormat createFormatARGB32(bool alpha=true)
Definition: pixelformat.h:234
static constexpr PixelFormat createFormatRGB24()
Definition: pixelformat.h:189
Common::String toString() const
void colorToARGB(uint32 color, uint8 &a, uint8 &r, uint8 &g, uint8 &b) const
Definition: pixelformat.h:309
uint rMax() const
Definition: pixelformat.h:373
byte bytesPerPixel
Definition: pixelformat.h:139
byte aBits() const
Definition: pixelformat.h:353
uint aMax() const
Definition: pixelformat.h:394
byte gBits() const
Definition: pixelformat.h:339
static constexpr PixelFormat createFormatBGRA32(bool alpha=true)
Definition: pixelformat.h:216
uint gMax() const
Definition: pixelformat.h:380
static constexpr PixelFormat createFormatBGR24()
Definition: pixelformat.h:198
byte bBits() const
Definition: pixelformat.h:346
byte aShift
Definition: pixelformat.h:142
uint bMax() const
Definition: pixelformat.h:387
static constexpr PixelFormat createFormatCLUT8()
Definition: pixelformat.h:184