File: Color.h

package info (click to toggle)
jazz2-native 3.5.0-2
  • links: PTS, VCS
  • area: contrib
  • in suites: forky, sid
  • size: 16,912 kB
  • sloc: cpp: 172,557; xml: 113; python: 36; makefile: 5; sh: 2
file content (168 lines) | stat: -rw-r--r-- 5,326 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
#pragma once

#include <Common.h>
#include <Containers/Tags.h>

namespace nCine
{
	inline namespace Primitives
	{
		class Colorf;

		using Death::Containers::NoInitT;

		/// Four-channel color with 8-bit integers per component
		class Color
		{
		public:
			/** @{ @name Constants */

			/** @brief Number of channels */
			static constexpr std::int32_t NumChannels = 4;

			/** @} */

			/** @{ @name Predefined colors */

			static const Color Black;
			static const Color White;
			static const Color Red;
			static const Color Green;
			static const Color Blue;
			static const Color Yellow;
			static const Color Magenta;
			static const Color Cyan;

			/** @} */

#if defined(DEATH_TARGET_BIG_ENDIAN)
			/** @brief Alpha */
			std::uint8_t A;  // Stored first (highest byte of std::uint32_t)
			/** @brief Blue */
			std::uint8_t B;
			/** @brief Green */
			std::uint8_t G;
			/** @brief Red */
			std::uint8_t R;  // Stored last (lowest byte of std::uint32_t)
#else
			/** @brief Red */
			std::uint8_t R;  // Stored first (lowest byte of std::uint32_t)
			/** @brief Green */
			std::uint8_t G;
			/** @brief Blue */
			std::uint8_t B;
			/** @brief Alpha */
			std::uint8_t A;  // Stored last (highest byte of std::uint32_t)
#endif

			/// Default constructor (transparent color)
			constexpr Color() noexcept
				: Color(0, 0, 0, 0) {}

			explicit Color(NoInitT) noexcept {}

			/// Three channels constructor
			constexpr Color(std::uint8_t red, std::uint8_t green, std::uint8_t blue) noexcept
				: Color(red, green, blue, 255) {}
			/// Four channels constructor
			constexpr Color(std::uint8_t red, std::uint8_t green, std::uint8_t blue, std::uint8_t alpha) noexcept
				: R(red), G(green), B(blue), A(alpha) {}
			/// Three channels constructor from a hexadecimal code
			explicit Color(std::uint32_t hex);
			/// Four channels constructor from an array
			explicit Color(const std::uint8_t channels[NumChannels]);
			explicit Color(const Colorf& color);

			/// Returns the color as a single RGBA unsigned integer
			std::uint32_t Rgba() const;
			/// Returns the color as a single RGBA unsigned integer
			std::uint32_t Argb() const;
			/// Returns the color as a single ABGR unsigned integer
			std::uint32_t Abgr() const;
			/// Returns the color as a single BGRA unsigned integer
			std::uint32_t Bgra() const;

			/// Returns color array
			inline const std::uint8_t* Data() const {
				return &R;
			}
			/// @overload
			inline std::uint8_t* Data() {
				return &R;
			}

			/// Sets four color channels
			constexpr void Set(std::uint8_t red, std::uint8_t green, std::uint8_t blue, std::uint8_t alpha)
			{
				R = red;
				G = green;
				B = blue;
				A = alpha;
			}
			/// Sets three color channels
			void Set(std::uint8_t red, std::uint8_t green, std::uint8_t blue);
			/// Sets three color channels from a hexadecimal code
			void Set(std::uint32_t hex);
			/// Sets four color channels from an array
			void SetVec(const std::uint8_t channels[NumChannels]);

			/// Sets the alpha channel
			void SetAlpha(std::uint8_t alpha);

			/// Assigns operator from a normalized float color
			Color& operator=(const Colorf& color);

			bool operator==(const Color& color) const;
			bool operator!=(const Color& color) const;

			Color& operator+=(const Color& v);
			Color& operator-=(const Color& v);

			Color& operator*=(const Color& color);
			/// Multiplies by a constant scalar
			Color& operator*=(float scalar);

			Color operator+(const Color& color) const;
			Color operator-(const Color& color) const;

			Color operator*(const Color& color) const;
			/// Multiplies by a constant scalar
			Color operator*(float scalar) const;
		};

		inline namespace Literals
		{
			// According to https://wg21.link/CWG2521, space between "" and literal name is deprecated because _Uppercase
			// or _double names could be treated as reserved depending on whether the space was present or not,
			// and whitespace is not load-bearing in any other contexts. Clang 17+ adds an off-by-default warning for this;
			// GCC 4.8 however *requires* the space there, so until GCC 4.8 support is dropped, we suppress this warning
			// instead of removing the space. GCC 15 now has the same warning but it's enabled by default on -std=c++23.
			#if (defined(DEATH_TARGET_CLANG) && __clang_major__ >= 17) || (defined(DEATH_TARGET_GCC) && !defined(DEATH_TARGET_CLANG) && __GNUC__ >= 15)
			#	pragma GCC diagnostic push
			#	pragma GCC diagnostic ignored "-Wdeprecated-literal-operator"
			#endif

			/** @relatesalso nCine::Primitives::Color
				@brief 8bit-per-channel RGB color literal

				See @ref Color for more information.
			*/
			constexpr Color operator"" _rgb(unsigned long long value) {
				return { std::uint8_t(value >> 16), std::uint8_t(value >> 8), std::uint8_t(value) };
			}

			/** @relatesalso nCine::Primitives::Color
				@brief 8bit-per-channel RGBA color literal

				See @ref Color for more information.
			*/
			constexpr Color operator"" _rgba(unsigned long long value) {
				return { std::uint8_t(value >> 24), std::uint8_t(value >> 16), std::uint8_t(value >> 8), std::uint8_t(value) };
			}

			#if (defined(DEATH_TARGET_CLANG) && __clang_major__ >= 17) || (defined(DEATH_TARGET_GCC) && !defined(DEATH_TARGET_CLANG) && __GNUC__ >= 15)
			#	pragma GCC diagnostic pop
			#endif
		}
	}
}