Use an absolute directory under /usr/share/games/ for game data
[kraptor.git] / src / mapa.c
blob652f9ae37124431d7b338b64d56e854a79df36c7
1 /*
2 --------------------------------------------------------
3 mapa.c
4 --------------------------------------------------------
5 Copyright (c) Kronoman
6 En memoria de mi querido padre
7 --------------------------------------------------------
8 Esto contiene todo lo referente al mapa en si
9 Hace scrollings, quema areas, impulsa nuevos enemigos, etc
10 Cargar un nuevo mapa esta en data.c :^P
11 Afecta el nivel de detalle a la calidad de los graficos...
12 --------------------------------------------------------
14 #ifndef MAPA_C
15 #define MAPA_C
17 #include "azar.h"
18 #include "kfbuffer.h"
19 #include "allegro.h"
20 #include "mapa.h"
21 #include "explos.h"
22 #include "enemigo.h"
23 #include "combo.h"
24 #include "global.h"
25 #include "sonido.h"
26 #include "humo.h"
28 /* Globales */
29 long mapa_g[GRILLA_W][GRILLA_H]; /* Grilla del mapa explosivo */
30 long enem_g[GRILLA_W][GRILLA_H]; /* Grilla de aparicion de enemigos */
32 int scroll_mapa = 0; /* scroll del mapa, en pixeles, va subiendo desde H_FONDO-ALTO_FB a 0 */
33 int scroll_mapa_speed = 1; /* velocidad de scroll de mapa, normalmente 1 */
35 COLOR_MAP tabla_quemado; /* tabla para realizar el 'quemado' del mapa con sprites */
36 BITMAP *burn_cache_bmp[3]; /* cache de sprites de 'quemado' */
38 /* Mapa de fondo */
39 BITMAP *mapa_fondo = NULL;
42 Esta funcion detona el fondo cuando los disparos le pegan.
43 Es recursiva.
44 Pasarle las coordenadas de los disparos en grilla
45 y el punch del disparo, si es -666, explota si o si!
46 El punch se va incrementando a medida que explota
47 Devuelve 0 si no toco nada, -1 si exploto y -2 si solo toco (para desaparecer el disparo)
49 int explotar_fondo(int x, int y, int punch)
52 /* fuera de grilla ? */
53 if (x < 0) return 0;
54 if (y < 0) return 0;
55 if (x > GRILLA_W-1) return 0;
56 if (y > GRILLA_H-1) return 0;
58 if (mapa_g[x][y] == 0) return 0; /* este sector no es explosivo */
60 if (mapa_g[x][y] > 0)
62 mapa_g[x][y] -= punch;
64 if (punch == -666)
66 mapa_g[x][y] = -1; /* explosion obligatoria */
67 punch = rand()%10+10; /* evita un bug que impide explosiones, dejando areas superduras */
70 if (mapa_g[x][y] <= 0) /* EXPLOTO! */
73 /* Quemar area (le paso el punto central en x,y) */
74 quemar_area(mapa_fondo, x * W_GR + W_GR/2+rand_ex(-5,5) , y * H_GR + H_GR/2+rand_ex(-5,5) , 30, 40);
76 /* explosion */
77 pone_explo_pixel(&ptr_explo_fondo,
78 x * W_GR + W_GR/2+rand_ex(-5,5),
79 y * H_GR + H_GR/2+rand_ex(-5,5),
80 rand()%W_GR/2+W_GR, rand()%W_GR/2+W_GR/2,
81 ftofix((float)(rand()%10+10)/1000.0) );
83 /* sonido */
84 tocar_sonido_paneado(x * W_GR,
85 explo_cache_snd[rand()%3],
86 rand_ex(32, 64),
87 rand_ex(800, 1200));
89 /* emisor de humo en el piso - WOW! */
90 agrega_emisor_humo(itofix(x * W_GR + W_GR/2 + rand_ex(-5,5)),
91 itofix(y * H_GR + H_GR/2 + rand_ex(-5,5)),
92 rand_ex(30,100));
94 mapa_g[x][y] = 0; /* seguridad */
95 /* explotar los 4 contiguos
96 (diagonales no son necesarias,
97 los contiguos las atrapan ),
99 DEBUG:
100 si explota el contiguo, quemar el area intermedia
101 para darle mas efecto. */
103 /* explosion obligatoria contigua */
104 explotar_fondo(x-1, y, -666);
105 explotar_fondo(x+1, y, -666);
106 explotar_fondo(x, y-1, -666);
107 explotar_fondo(x, y+1, -666);
109 return -1; /* EXPLOTO */
112 /* no exploto, pero toco, explotar poquisimo */
113 pone_explo_pixel(&ptr_explo_fondo,
114 x * W_GR + W_GR/2+rand_ex(-5,5),
115 y * H_GR + H_GR/2+rand_ex(-5,5),
116 rand()%10+10, rand()%10+10,
117 ftofix((float)(rand()%10+10)/1000.0) );
119 return -2;
122 if (mapa_g[x][y] < 0) mapa_g[x][y] = 0; /* seguridad */
123 return 0;
127 Esta funcion se llama cuando inicia un nuevo nivel, para escanear todas
128 las lineas visibles de mapa en la primera pantalla
130 void scan_nivel_1era_vez()
132 int y;
133 for (y=H_FONDO-ALTO_FB; y < H_FONDO; y++) scan_nuevos_enemigos(y / H_GR);
137 Esta funcion escanea una linea de la grilla
138 y agrega los nuevos enemigos.
139 Pasar en y la linea de la grilla a escanear (no pixels!)
140 NOTA: Por lo general sera: scroll_mapa / H_GR
142 void scan_nuevos_enemigos(int y)
144 int x;
145 int cx, cy; // para calcular el centro, auxiliares
147 if (y < 0) y = 0;
148 if (y > GRILLA_H-1) y = GRILLA_H-1;
150 for (x = 0; x < GRILLA_W; x++)
153 // coloca el enemigo centrado...
154 if (enem_g[x][y] > 0)
156 // desplazamiento para centrarlo
157 cx = (W_GR / 2) - (enem_t[enem_g[x][y]-1].spr[0]->w / 2);
158 cy = (H_GR / 2) - (enem_t[enem_g[x][y]-1].spr[0]->h / 2);
160 // agregarlo...
161 agregar_enemigo(cx + (x*W_GR), cy + (y*H_GR), enem_g[x][y]-1 );
164 /* cada linea escaneada se coloca a 0, para no volver a usarla */
165 enem_g[x][y] = 0;
170 Esta funcion quema un area del bitmap
171 utiliza funciones de transparencia
172 Pasarle las coordenadas en pixeles y el bmp a 'quemar'
173 ademas del radio del impacto (rad1) y el radio de las esquirlas (rad2)
175 Las coordenadas son el *centro* de la quemazon!
177 NOTA: mucho fue desabilitado a proposito (aunque funciona) porque
178 queda mas lindo de esta manera... ;^)
181 void quemar_area(BITMAP *bmp, int xp, int yp, int rad1, int rad2)
183 int x = xp, y = yp, r = 0, i = 0 , c = 0, c2 = 0;
184 COLOR_MAP *color_map_bak = color_map; /* para restaur el color map */
186 // solid_mode();
188 drawing_mode(DRAW_MODE_TRANS, NULL, 0,0);
191 /* Impacto circular */
193 // c = makecol(0,0,0);
196 // r = rand_ex(nivel_detalle/2, nivel_detalle);
197 // r=r+2;
198 // for(i =0; i < r; i++)
199 // {
200 // c2 = rand()%16;
201 // c = makecol(c2,c2,c2);
202 // circlefill(bmp,
203 // x + rand_ex(-rad1/4, rad1/4), y + rand_ex(-rad1/4, rad1/4),
204 // rand_ex(rad1/4, rad1/2 ), c); /* entre 1/4 y 1/2 del radio */
205 // }
208 /* Esquirlas */
209 r = rand_ex(nivel_detalle/2, nivel_detalle);
210 r=r+2;
211 for(i =0; i < r; i++)
213 c2 = rand()%64;
214 c = makecol(c2,c2,c2);
216 //if (rand()%100 < 30)
217 // line(bmp, x, y, x + rand_ex(-rad2, rad2), y + rand_ex(-rad2, rad2), c);
218 //else
219 triangle(bmp,
220 x + rand_ex(-rad2/3, rad2/3), y + rand_ex(-rad2/3, rad2/3),
221 x + rand_ex(-rad2/3, rad2/3), y + rand_ex(-rad2/3, rad2/3),
222 x + rand_ex(-rad2, rad2), y + rand_ex(-rad2, rad2), c);
226 /* Sub impacto triangular */
227 // r = rand_ex(nivel_detalle/3, nivel_detalle/2);
228 // r=r+2;
229 // for(i =0; i < r; i++)
230 // {
231 // c2 = rand()%32;
232 // c = makecol(c2,c2,c2);
234 // triangle(bmp,
235 // x + rand_ex(-rad1, rad1), y + rand_ex(-rad1, rad1),
236 // x + rand_ex(-rad1, rad1), y + rand_ex(-rad1, rad1),
237 // x + rand_ex(-rad1, rad1), y + rand_ex(-rad1, rad1), c);
238 // }
240 solid_mode();
242 // DEBUG: nuevo metodo, usa un sprite transparente rotado
243 // y un efecto de 'burn'
244 color_map = &tabla_quemado;
245 /* centrar el bitmap de quemazon */
246 c = rand_ex(0,2);
247 x = xp - burn_cache_bmp[c]->w / 2;
248 y = yp - burn_cache_bmp[c]->h / 2;
249 draw_trans_sprite(mapa_fondo, burn_cache_bmp[c], x, y);
250 color_map = color_map_bak;
256 /* Esta funcion crea el mapa de transparencias
257 necesario para quemar, donde los tonos de negro dejan
258 el color igual, y los blancos queman el fondo
259 llamar:
260 create_color_table(&tabla_a_crear,
261 paleta_a_usar,
262 crear_mapa_quemazon,
263 NULL);
265 NOTA: x es el color a dibujar
266 y es el color sobre el que se dibuja
270 void crear_mapa_quemazon(AL_CONST PALETTE pal, int x, int y, RGB *rgb)
272 int r, g, b, r2, g2, b2;
273 float h,s,v, h2,s2,v2;
275 r = (int)pal[x].r;
276 g = (int)pal[x].g;
277 b = (int)pal[x].b;
279 r2 = (int)pal[y].r;
280 g2 = (int)pal[y].g;
281 b2 = (int)pal[y].b;
283 /* si el color es suficientemente claro (oscuro para quemar), usarlo */
284 if (r > 3 && g > 3 && b > 3)
286 /* invertir el color */
287 r = 63 - r;
288 g = 63 - g;
289 b = 63 - b;
291 /* no permitir demasiado brillo */
292 r = MIN(48, r);
293 g = MIN(48, g);
294 b = MIN(48, b);
296 /* tonalizar color destino (mult/div por 4 porque es 0..255) */
297 rgb_to_hsv(r*4, g*4, b*4, &h, &s, &v);
299 rgb_to_hsv(r2*4, g2*4, b2*4, &h2, &s2, &v2);
301 /* tomo el valor minimo de luz, para que las cosas muy oscuras
302 no sean afectadas y aclaradas por mi quemazon (quedaria mal) */
303 hsv_to_rgb(h2, s2, MIN(v, v2), &r, &g, &b);
305 r /= 4;
306 g /= 4;
307 b /= 4;
309 else /* dejar color original */
311 r = r2;
312 g = g2;
313 b = b2;
316 rgb->r = r;
317 rgb->g = g;
318 rgb->b = b;
319 } // fin crear_mapa_aditivo
322 #endif