]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/blob - qcsrc/lib/color.qh
Merge branch 'master' into Mario/speed_var
[xonotic/xonotic-data.pk3dir.git] / qcsrc / lib / color.qh
1 #pragma once
2
3 #include "string.qh"
4
5 #define colormapPaletteColor(c, isPants) colormapPaletteColor_(c, isPants, time)
6 ERASEABLE
7 vector colormapPaletteColor_(int c, bool isPants, float t)
8 {
9         // these colors are defined in gfx/colormap_palette.pl
10         // to generate them run: perl gfx/colormap_palette.pl > gfx/colormap_palette.lmp
11         // it will save them to gfx/colormap_palette.lmp (in the lmp format)
12         // and prints the cases of the following switch so they can be copy-pasted here
13
14         switch (c)
15         {
16                 // generated by gfx/colormap_palette.pl
17                 case  0: return '1.000000 1.000000 1.000000';
18                 case  1: return '1.000000 0.333333 0.000000';
19                 case  2: return '0.000000 1.000000 0.501961';
20                 case  3: return '0.000000 1.000000 0.000000';
21                 case  4: return '1.000000 0.000000 0.000000';
22                 case  5: return '0.000000 0.666667 1.000000';
23                 case  6: return '0.000000 1.000000 1.000000';
24                 case  7: return '0.501961 1.000000 0.000000';
25                 case  8: return '0.501961 0.000000 1.000000';
26                 case  9: return '1.000000 0.000000 1.000000';
27                 case 10: return '1.000000 0.000000 0.501961';
28                 case 11: return '0.000000 0.000000 1.000000';
29                 case 12: return '1.000000 1.000000 0.000000';
30                 case 13: return '0.000000 0.333333 1.000000';
31                 case 14: return '1.000000 0.666667 0.000000';
32                 case 15:
33                         if (isPants)
34                                 return '1 0 0' * (0.502 + 0.498 * sin(t / M_E + 0))
35                                         + '0 1 0' * (0.502 + 0.498 * sin(t / M_E + M_PI * 2 / 3))
36                                         + '0 0 1' * (0.502 + 0.498 * sin(t / M_E + M_PI * 4 / 3));
37                         else
38                                 return '1 0 0' * (0.502 + 0.498 * sin(t / M_PI + M_PI * 5 / 3))
39                                         + '0 1 0' * (0.502 + 0.498 * sin(t / M_PI + M_PI))
40                                         + '0 0 1' * (0.502 + 0.498 * sin(t / M_PI + M_PI * 1 / 3));
41                 default: return '0.000 0.000 0.000';
42         }
43 }
44
45 ERASEABLE
46 float rgb_mi_ma_to_hue(vector rgb, float mi, float ma)
47 {
48         if (mi == ma)
49         {
50                 return 0;
51         }
52         else if (ma == rgb.x)
53         {
54                 if (rgb.y >= rgb.z) return (rgb.y - rgb.z) / (ma - mi);
55                 else return (rgb.y - rgb.z) / (ma - mi) + 6;
56         }
57         else if (ma == rgb.y)
58         {
59                 return (rgb.z - rgb.x) / (ma - mi) + 2;
60         }
61         else  // if(ma == rgb_z)
62         {
63                 return (rgb.x - rgb.y) / (ma - mi) + 4;
64         }
65 }
66
67 ERASEABLE
68 vector hue_mi_ma_to_rgb(float hue, float mi, float ma)
69 {
70         vector rgb;
71
72         hue -= 6 * floor(hue / 6);
73
74         // else if(ma == rgb_x)
75         //      hue = 60 * (rgb_y - rgb_z) / (ma - mi);
76         if (hue <= 1)
77         {
78                 rgb.x = ma;
79                 rgb.y = hue * (ma - mi) + mi;
80                 rgb.z = mi;
81         }
82         // else if(ma == rgb_y)
83         //      hue = 60 * (rgb_z - rgb_x) / (ma - mi) + 120;
84         else if (hue <= 2)
85         {
86                 rgb.x = (2 - hue) * (ma - mi) + mi;
87                 rgb.y = ma;
88                 rgb.z = mi;
89         }
90         else if (hue <= 3)
91         {
92                 rgb.x = mi;
93                 rgb.y = ma;
94                 rgb.z = (hue - 2) * (ma - mi) + mi;
95         }
96         // else // if(ma == rgb_z)
97         //      hue = 60 * (rgb_x - rgb_y) / (ma - mi) + 240;
98         else if (hue <= 4)
99         {
100                 rgb.x = mi;
101                 rgb.y = (4 - hue) * (ma - mi) + mi;
102                 rgb.z = ma;
103         }
104         else if (hue <= 5)
105         {
106                 rgb.x = (hue - 4) * (ma - mi) + mi;
107                 rgb.y = mi;
108                 rgb.z = ma;
109         }
110         // else if(ma == rgb_x)
111         //      hue = 60 * (rgb_y - rgb_z) / (ma - mi);
112         else  // if(hue <= 6)
113         {
114                 rgb.x = ma;
115                 rgb.y = mi;
116                 rgb.z = (6 - hue) * (ma - mi) + mi;
117         }
118
119         return rgb;
120 }
121
122 ERASEABLE
123 vector rgb_to_hsv(vector rgb)
124 {
125         float mi, ma;
126         vector hsv;
127
128         mi = min(rgb.x, rgb.y, rgb.z);
129         ma = max(rgb.x, rgb.y, rgb.z);
130
131         hsv.x = rgb_mi_ma_to_hue(rgb, mi, ma);
132         hsv.z = ma;
133
134         if (ma == 0) hsv.y = 0;
135         else hsv.y = 1 - mi / ma;
136
137         return hsv;
138 }
139
140 ERASEABLE
141 vector hsv_to_rgb(vector hsv)
142 {
143         return hue_mi_ma_to_rgb(hsv.x, hsv.z * (1 - hsv.y), hsv.z);
144 }
145
146 ERASEABLE
147 vector rgb_to_hsl(vector rgb)
148 {
149         float mi, ma;
150         vector hsl;
151
152         mi = min(rgb.x, rgb.y, rgb.z);
153         ma = max(rgb.x, rgb.y, rgb.z);
154
155         hsl.x = rgb_mi_ma_to_hue(rgb, mi, ma);
156
157         hsl.z = 0.5 * (mi + ma);
158         if (mi == ma) hsl.y = 0;
159         else if (hsl.z <= 0.5) hsl.y = (ma - mi) / (2 * hsl.z);
160         else  // if(hsl_z > 0.5)
161                 hsl.y = (ma - mi) / (2 - 2 * hsl.z);
162
163         return hsl;
164 }
165
166 ERASEABLE
167 vector hsl_to_rgb(vector hsl)
168 {
169         float mi, ma, maminusmi;
170
171         if (hsl.z <= 0.5) maminusmi = hsl.y * 2 * hsl.z;
172         else maminusmi = hsl.y * (2 - 2 * hsl.z);
173
174         // hsl_z     = 0.5 * mi + 0.5 * ma
175         // maminusmi =     - mi +       ma
176         mi = hsl.z - 0.5 * maminusmi;
177         ma = hsl.z + 0.5 * maminusmi;
178
179         return hue_mi_ma_to_rgb(hsl.x, mi, ma);
180 }
181
182 ERASEABLE
183 string rgb_to_hexcolor(vector rgb)
184 {
185         return strcat(
186                 "^x",
187                 DEC_TO_HEXDIGIT(floor(rgb.x * 15 + 0.5)),
188                 DEC_TO_HEXDIGIT(floor(rgb.y * 15 + 0.5)),
189                 DEC_TO_HEXDIGIT(floor(rgb.z * 15 + 0.5))
190                      );
191 }