1 /* $Id: palette.c,v 1.11 2004-05-12 22:06:02 btb Exp $ */
3 THE COMPUTER CODE CONTAINED HEREIN IS THE SOLE PROPERTY OF PARALLAX
4 SOFTWARE CORPORATION ("PARALLAX"). PARALLAX, IN DISTRIBUTING THE CODE TO
5 END-USERS, AND SUBJECT TO ALL OF THE TERMS AND CONDITIONS HEREIN, GRANTS A
6 ROYALTY-FREE, PERPETUAL LICENSE TO SUCH END-USERS FOR USE BY SUCH END-USERS
7 IN USING, DISPLAYING, AND CREATING DERIVATIVE WORKS THEREOF, SO LONG AS
8 SUCH USE, DISPLAY OR CREATION IS FOR NON-COMMERCIAL, ROYALTY OR REVENUE
9 FREE PURPOSES. IN NO EVENT SHALL THE END-USER USE THE COMPUTER CODE
10 CONTAINED HEREIN FOR REVENUE-BEARING PURPOSES. THE END-USER UNDERSTANDS
11 AND AGREES TO THE TERMS HEREIN AND ACCEPTS THE SAME BY USE OF THIS FILE.
12 COPYRIGHT 1993-1998 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
16 * Graphical routines for setting the palette
19 * Revision 1.41 1995/02/02 14:26:31 john
20 * Made palette fades work better with gamma thingy..
22 * Revision 1.40 1994/12/08 19:03:46 john
23 * Made functions use cfile.
25 * Revision 1.39 1994/12/01 11:23:27 john
26 * Limited Gamma from 0-8.
28 * Revision 1.38 1994/11/28 01:31:08 mike
29 * optimize color lookup function, caching recently used colors.
31 * Revision 1.37 1994/11/18 22:50:18 john
32 * Changed shorts to ints in parameters.
34 * Revision 1.36 1994/11/15 17:54:59 john
35 * Made text palette fade in when game over.
37 * Revision 1.35 1994/11/10 19:53:14 matt
38 * Fixed error handling is gr_use_palette_table()
40 * Revision 1.34 1994/11/07 13:53:48 john
41 * Added better gamma stufff.
43 * Revision 1.33 1994/11/07 13:37:56 john
44 * Added gamma correction stuff.
46 * Revision 1.32 1994/11/05 13:20:14 john
47 * Fixed bug with find_closest_color_current not working.
49 * Revision 1.31 1994/11/05 13:08:09 john
50 * MAde it return 0 when palette already faded out.
52 * Revision 1.30 1994/11/05 13:05:34 john
53 * Added back in code to allow keys during fade.
55 * Revision 1.29 1994/11/05 12:49:50 john
56 * Fixed bug with previous comment..
58 * Revision 1.28 1994/11/05 12:48:46 john
59 * Made palette only fade in / out when its supposed to.
61 * Revision 1.27 1994/11/05 12:46:43 john
62 * Changed palette stuff a bit.
64 * Revision 1.26 1994/11/01 12:59:35 john
65 * Reduced palette.256 size.
67 * Revision 1.25 1994/10/26 23:55:35 john
68 * Took out roller; Took out inverse table.
70 * Revision 1.24 1994/10/04 22:03:05 matt
71 * Fixed bug: palette wasn't fading all the way out or in
73 * Revision 1.23 1994/09/22 16:08:40 john
74 * Fixed some palette stuff.
76 * Revision 1.22 1994/09/19 11:44:31 john
77 * Changed call to allocate selector to the dpmi module.
79 * Revision 1.21 1994/09/12 19:28:09 john
80 * Fixed bug with unclipped fonts clipping.
82 * Revision 1.20 1994/09/12 18:18:39 john
83 * Set 254 and 255 to fade to themselves in fadetable
85 * Revision 1.19 1994/09/12 14:40:10 john
88 * Revision 1.18 1994/09/09 09:31:55 john
89 * Made find_closest_color not look at superx spot of 254
91 * Revision 1.17 1994/08/09 11:27:08 john
94 * Revision 1.16 1994/08/01 11:03:51 john
95 * MAde it read in old/new palette.256
97 * Revision 1.15 1994/07/27 18:30:27 john
98 * Took away the blending table.
100 * Revision 1.14 1994/06/09 10:39:52 john
101 * In fade out.in functions, returned 1 if key was pressed...
103 * Revision 1.13 1994/05/31 19:04:16 john
104 * Added key to stop fade if desired.
106 * Revision 1.12 1994/05/06 12:50:20 john
107 * Added supertransparency; neatend things up; took out warnings.
109 * Revision 1.11 1994/05/03 19:39:02 john
110 * *** empty log message ***
112 * Revision 1.10 1994/04/22 11:16:07 john
113 * *** empty log message ***
115 * Revision 1.9 1994/04/08 16:59:40 john
116 * Add fading poly's; Made palette fade 32 instead of 16.
118 * Revision 1.8 1994/03/16 17:21:17 john
119 * Added slow palette searching options.
121 * Revision 1.7 1994/01/07 11:47:33 john
124 * Revision 1.6 1993/12/21 11:41:04 john
125 * *** empty log message ***
127 * Revision 1.5 1993/12/09 15:02:47 john
128 * Changed palette stuff majorly
130 * Revision 1.4 1993/12/07 12:31:41 john
131 * moved bmd_palette to gr_palette
133 * Revision 1.3 1993/10/15 16:22:23 john
134 * *** empty log message ***
136 * Revision 1.2 1993/09/26 18:59:46 john
139 * Revision 1.1 1993/09/08 11:44:03 john
160 //added/remove by dph on 1/9/99
166 extern int gr_installed;
168 #define SQUARE(x) ((x)*(x))
170 #define MAX_COMPUTED_COLORS 32
172 int Num_computed_colors=0;
175 ubyte r,g,b,color_num;
178 color_record Computed_colors[MAX_COMPUTED_COLORS];
180 ubyte gr_palette[256*3];
181 ubyte gr_current_pal[256*3];
182 ubyte gr_fade_table[256*34];
184 ubyte gr_palette_gamma = 0;
185 int gr_palette_gamma_param = 0;
186 ubyte gr_palette_faded_out = 1;
188 int grd_fades_disabled=0; // Used to skip fading for development
190 void gr_palette_set_gamma( int gamma )
192 if ( gamma < 0 ) gamma = 0;
193 //added/changed on 10/27/98 by Victor Rachels to increase brightness slider
194 if ( gamma > 16 ) gamma = 16; //was 8
195 //end this section change - Victor Rachels
197 if (gr_palette_gamma_param != gamma ) {
198 gr_palette_gamma_param = gamma;
199 gr_palette_gamma = gamma;
200 if (!gr_palette_faded_out)
201 gr_palette_load( gr_palette );
205 int gr_palette_get_gamma()
207 return gr_palette_gamma_param;
211 void gr_copy_palette(ubyte *gr_palette, ubyte *pal, int size)
213 memcpy(gr_palette, pal, size);
215 Num_computed_colors = 0;
219 void gr_use_palette_table( char * filename )
227 fp = cfopen( filename, "rb" );
229 // the following is a hack to enable the loading of d2 levels
230 // even if only the d2 mac shareware datafiles are present.
231 // However, if the pig file is present but the palette file isn't,
232 // the textures in the level will look wierd...
234 fp = cfopen( DEFAULT_LEVEL_PALETTE, "rb" );
236 Error("Can open neither palette file <%s> "
237 "nor default palette file <"
238 DEFAULT_LEVEL_PALETTE
242 fsize = cfilelength( fp );
243 Assert( fsize == 9472 );
244 cfread( gr_palette, 256*3, 1, fp );
245 cfread( gr_fade_table, 256*34, 1, fp );
248 // This is the TRANSPARENCY COLOR
249 for (i=0; i<GR_FADE_LEVELS; i++ ) {
250 gr_fade_table[i*256+255] = 255;
253 Num_computed_colors = 0; // Flush palette cache.
254 #if defined(POLY_ACC)
255 pa_update_clut(gr_palette, 0, 256, 0);
258 // swap colors 0 and 255 of the palette along with fade table entries
261 for (i = 0; i < 3; i++) {
263 gr_palette[i] = gr_palette[765+i];
264 gr_palette[765+i] = c;
267 for (i = 0; i < GR_FADE_LEVELS * 256; i++) {
268 if (gr_fade_table[i] == 0)
269 gr_fade_table[i] = 255;
271 for (i=0; i<GR_FADE_LEVELS; i++)
272 gr_fade_table[i*256] = TRANSPARENCY_COLOR;
276 // Add a computed color (by gr_find_closest_color) to list of computed colors in Computed_colors.
277 // If list wasn't full already, increment Num_computed_colors.
278 // If was full, replace a random one.
279 void add_computed_color(int r, int g, int b, int color_num)
283 if (Num_computed_colors < MAX_COMPUTED_COLORS) {
284 add_index = Num_computed_colors;
285 Num_computed_colors++;
287 add_index = (d_rand() * MAX_COMPUTED_COLORS) >> 15;
289 Computed_colors[add_index].r = r;
290 Computed_colors[add_index].g = g;
291 Computed_colors[add_index].b = b;
292 Computed_colors[add_index].color_num = color_num;
295 void init_computed_colors(void)
299 for (i=0; i<MAX_COMPUTED_COLORS; i++)
300 Computed_colors[i].r = 255; // Make impossible to match.
303 int gr_find_closest_color( int r, int g, int b )
306 int best_value, best_index, value;
308 if (Num_computed_colors == 0)
309 init_computed_colors();
311 // If we've already computed this color, return it!
312 for (i=0; i<Num_computed_colors; i++)
313 if (r == Computed_colors[i].r)
314 if (g == Computed_colors[i].g)
315 if (b == Computed_colors[i].b) {
318 trec = Computed_colors[i-1];
319 Computed_colors[i-1] = Computed_colors[i];
320 Computed_colors[i] = trec;
321 return Computed_colors[i-1].color_num;
323 return Computed_colors[i].color_num;
330 best_value = SQUARE(r-gr_palette[0])+SQUARE(g-gr_palette[1])+SQUARE(b-gr_palette[2]);
333 add_computed_color(r, g, b, best_index);
337 // only go to 255, 'cause we dont want to check the transparent color.
338 for (i=1; i<254; i++ ) {
340 value = SQUARE(r-gr_palette[j])+SQUARE(g-gr_palette[j+1])+SQUARE(b-gr_palette[j+2]);
341 if ( value < best_value ) {
343 add_computed_color(r, g, b, i);
350 add_computed_color(r, g, b, best_index);
354 int gr_find_closest_color_15bpp( int rgb )
356 return gr_find_closest_color( ((rgb>>10)&31)*2, ((rgb>>5)&31)*2, (rgb&31)*2 );
360 int gr_find_closest_color_current( int r, int g, int b )
363 int best_value, best_index, value;
369 best_value = SQUARE(r-gr_current_pal[0])+SQUARE(g-gr_current_pal[1])+SQUARE(b-gr_current_pal[2]);
375 // only go to 255, 'cause we dont want to check the transparent color.
376 for (i=1; i<254; i++ ) {
378 value = SQUARE(r-gr_current_pal[j])+SQUARE(g-gr_current_pal[j+1])+SQUARE(b-gr_current_pal[j+2]);
379 if ( value < best_value ) {
389 void gr_make_cthru_table(ubyte * table, ubyte r, ubyte g, ubyte b )
394 for (i=0; i<256; i++ ) {
395 r1 = gr_palette[i*3+0] + r;
396 if ( r1 > 63 ) r1 = 63;
397 g1 = gr_palette[i*3+1] + g;
398 if ( g1 > 63 ) g1 = 63;
399 b1 = gr_palette[i*3+2] + b;
400 if ( b1 > 63 ) b1 = 63;
401 table[i] = gr_find_closest_color( r1, g1, b1 );
405 void gr_make_blend_table(ubyte *blend_table, ubyte r, ubyte g, ubyte b)
411 for (j = 0; j < GR_FADE_LEVELS; j++)
413 alpha = 1.0 - (float)j / ((float)GR_FADE_LEVELS - 1);
414 for (i = 0; i < 255; i++)
416 r1 = (ubyte)((1.0 - alpha) * (float)gr_palette[i * 3 + 0] + (alpha * (float)r));
417 g1 = (ubyte)((1.0 - alpha) * (float)gr_palette[i * 3 + 1] + (alpha * (float)g));
418 b1 = (ubyte)((1.0 - alpha) * (float)gr_palette[i * 3 + 2] + (alpha * (float)b));
419 blend_table[i + j * 256] = gr_find_closest_color(r1, g1, b1);
421 blend_table[i + j * 256] = 255; // leave white alone