#include #include #include #include #include #include #include /* P.K. */ #include "macros.h" #include "types.h" #include "common.h" #include "main.h" #include "sprites.h" #include "options.h" #include "pouvoirs.h" #include "evenements.h" #include "son.h" Pouvoir teleporte={teleporte_f, 165, INSTANT}; Pouvoir touteteindre={touteteindre_f, 170, INSTANT}; Pouvoir detonateur={detonateur_f, 190, INSTANT}; //Pouvoir melange={melange_f, 200, INSTANT}; Pouvoir bigexplosion={bigexplosion_f, 250, INSTANT}; Pouvoir deguisement={deguisement_f, 120, DELAI}; Pouvoir bouclier={bouclier_f, 130, DELAI}; Pouvoir plusdefeu={plusdefeu_f, 150, DELAI}; Pouvoir invisible={invisible_f, 150, DELAI}; Pouvoir furie={furie_f, 155, DELAI}; Pouvoir vitesse={vitesse_f, 180, DELAI}; Pouvoir passemur={passemur_f, 200, DELAI}; Pouvoir superbombes={superbombes_f, 150, COMPTEUR}; /*--Effets graphiques pour les pouvoirs--*/ SDL_Color * chpal(float rmul, float gmul, float bmul, int debut, int fin) { int i; //int moy; SDL_Color *pal, *degrad; pal=(SDL_Color *)calloc(fin-debut, sizeof(SDL_Color)); degrad=(SDL_Color *)calloc(fin-debut, sizeof(SDL_Color)); for (i=debut; iformat->palette->ncolors; i++) { pal[i-debut].r=ecran->format->palette->colors[i].r; pal[i-debut].g=ecran->format->palette->colors[i].g; pal[i-debut].b=ecran->format->palette->colors[i].b; //moy=(pal[i-debut].r+pal[i-debut].g+pal[i-debut].b)/3; degrad[i-debut].r=pal[i-debut].r*rmul; degrad[i-debut].g=pal[i-debut].g*gmul; degrad[i-debut].b=pal[i-debut].b*bmul; } SDL_SetColors(ecran, degrad, debut, fin-debut); return pal; } paletsg changepalette(float rmul, float gmul, float bmul, int debut1, int fin1, int debut2, int fin2, int v) { int i; paletsg p; p.debut1=debut1; p.debut2=debut2; p.fin1=fin1; p.fin2=fin2; p.pal1=chpal(1-(1-rmul)/v, 1-(1-gmul)/v, 1-(1-bmul)/v, debut1, fin1); p.pal2=chpal(1-(1-rmul)/v, 1-(1-gmul)/v, 1-(1-bmul)/v, debut2, fin2); for (i=v-1; i>0; i--) { chpal(1-(1-rmul)/i, 1-(1-gmul)/i, 1-(1-bmul)/i, debut1, fin1); chpal(1-(1-rmul)/i, 1-(1-gmul)/i, 1-(1-bmul)/i, debut2, fin2); } return p; } void restorepalette(paletsg p, int v) { int i, ncoul, n; SDL_Color *pal, *ecrpal; ncoul=ecran->format->palette->ncolors; pal=(SDL_Color *)calloc(ncoul, sizeof(SDL_Color)); ecrpal=ecran->format->palette->colors; for (i=0; i=0; n--) { for (i=p.debut1; irebours=-1, pt=pt->suiv; } perso[n].pouvactif[p]=0; } return; } void detonateur_f(int n, int p, int action) { if (action==ACTIVATION) { perso[n].statut |= DETONATEUR; posebombe(perso[n].pos.x, perso[n].pos.y, n); perso[n].pouvactif[p]=0; } return; } #if 0 /* Incompatible avec le déguisement */ void melange_f(int n, int p, int action) { Coord co; int decal, i, mv, anim; if (action==ACTIVATION) { for (i=3; i>=0; i--) { SDL_FillRect(ecran, &tout, i); SDL_Flip(ecran); } rdplateau(0); dessinebande(); if (!catremble) { evtsplus(vibre, 0, 0, 0, 0, 15, 0, APRES, catremblefini); catremble=1; } for (i=0; idecalage + sprit[n]->palette->ncolors; pal=changepalette(1, 0, 0, 8, sprit[n]->decalage, ncoul, ecran->format->palette->ncolors, 10); /* Tout devient rouge */ contenu = SDL_DisplayFormat(ecran); for (deuxfois=0; deuxfois<2; deuxfois++) /* Et un tremblement de terre ! */ { bruitsplus(s_expl, 1); for (i=0; i<50; i++) { orig.x = orig.y = 0; //x sortie.w=orig.w=640; sortie.w = orig.w = resolution.window_width; //x sortie.h=orig.h=480; sortie.h = orig.h = resolution.window_height; sortie.x=aleat(2*15)-15; sortie.y=aleat(2*15)-15; SDL_FillRect(ecran, &tout, 0); SDL_BlitSurface(contenu, &orig, ecran, &sortie); SDL_LockSurface(ecran); for (j=0; j<2000; j++) { //x var=2.0*3.1415927*j/2000.0; var=2.0*PI*j/2000.0; dec=(2.0*rand())/(float)RAND_MAX-1; //x x=512/2+(int)((7+dec)*i*cos(var)); x = resolution.x_offset+(resolution.plan_width)/2+(int)((7+dec)*i*cos(var)); //x y=480/2+(int)((7+dec)*i*sin(var)); y = resolution.y_offset+(resolution.plan_height)/2+(int)((7+dec)*i*sin(var)); //x if (0<=x && x<640 && 0<=y && y<480) if (0 <= x && x < resolution.window_width && 0 <= y && y < resolution.window_height) //x ((Uint8 *)ecran->pixels)[y*640+x]=(Uint8)(4-2.9*fabs(dec)); ((Uint8 *)ecran->pixels)[y*resolution.window_width+x] = (Uint8)(4-2.9*fabs(dec)); } SDL_UnlockSurface(ecran); //x blitsprit(sprit[n], SUPER2, 0, (512-32)/2, 480/2-32); blitsprit(sprit[n], SUPER2, 0, (resolution.plan_width-32)/2, resolution.plan_height/2-32); //x blitsprit(sprit[n], SUPER2, 1, (512-32)/2, 480/2); blitsprit(sprit[n], SUPER2, 1, (resolution.plan_width-32)/2, resolution.plan_height/2); SDL_Flip(ecran); } } //tremblementdeterre(15, 30); bruitsplus(s_expl, 1); for (i=3; i>=0; i--) /* Un éclair */ { SDL_FillRect(ecran, &tout, i); SDL_Delay(VITESSE); SDL_Flip(ecran); } SDL_BlitSurface(contenu, &tout, ecran, &tout); if (dblebuf) { SDL_Flip(ecran); SDL_BlitSurface(contenu, &tout, ecran, &tout); } restorepalette(pal, 50); SDL_FreeSurface(contenu); for (i=0; irebours=15, pt=pt->suiv; } perso[n].pouvactif[p]=0; } return; } /*--Pouvoirs de durée--*/ void deguisement_f(int n, int p, int action) { if (action==ACTIVATION) { if ( !(perso[n].statut & DEGUISE) ) { perso[n].statut |= DEGUISE; perso[n].pouvoirparam=plan.element[perso[n].pos.x][perso[n].pos.y].type; plan.element[perso[n].pos.x][perso[n].pos.y].type=CAMOUFL; } perso[n].animdroite=SUPER; perso[n].pouvactif[p]=300; } else if (action==TERMINE) { if (plan.element[perso[n].pos.x][perso[n].pos.y].type==CAMOUFL) plan.element[perso[n].pos.x][perso[n].pos.y].type=perso[n].pouvoirparam; perso[n].pouvoirparam=0; if (perso[n].statut & DEGUISE) perso[n].statut ^= DEGUISE; perso[n].animdroite=REPOS; } return; } void bouclier_f(int n, int p, int action) { if (action==ACTIVATION) { perso[n].statut |= INVINCIBLE; perso[n].pouvactif[p]=50; evtsplus(super, n, 0, 0, 0, 50, 0, APRES, NULL); } else if (action==TERMINE) { if (perso[n].statut & INVINCIBLE) perso[n].statut ^= INVINCIBLE; } return; } void plusdefeu_f(int n, int p, int action) { int i; if (action==ACTIVATION) { for (i=0; idecalage + sprit[n]->palette->ncolors; pal=changepalette(0.2, 0.2, 1, 8, sprit[n]->decalage, ncoul, ecran->format->palette->ncolors, 10); /* Tout devient bleu */ //x X = perso[n].pixpos.x+16; X = resolution.x_offset+perso[n].pixpos.x+16; //x Y = perso[n].pixpos.y+16; Y = resolution.y_offset+perso[n].pixpos.y+16; for (i=0; i<60; i++) { pix[i].x=aleat(50)-25+i; pix[i].y=250+aleat(80)-40; } for (i=0; i<50; i++) { if (SDL_LockSurface(ecran)<0) errormessage("SDL ne peut pas verrouiller l'écran", NULL); for (j=0; j<60; j++) { pix[j].x*=0.9; pix[j].y*=0.9; for (T=T0; Tpixels) [y*640+x] = aleat(3)+4; ((Uint8 *)ecran->pixels) [y*resolution.window_width+x] = aleat(3)+4; } } SDL_UnlockSurface(ecran); T0+=0.1; //SDL_Delay(20); SDL_Flip(ecran); } restorepalette(pal, 60); rdplateau(0); perso[n].statut |= INVISIBLE; perso[n].pouvactif[p]=250; } else if (action==TERMINE) { if (perso[n].statut & INVISIBLE) perso[n].statut ^= INVISIBLE; } return; } void furie_f(int n, int p, int action) { if (action == ACTIVATION) { perso[n].statut |= FURIEDESTRUCTRICE|INVISIBLE; evtsplus(super, n, 0, 0, 0, 80, 0, APRES, NULL); perso[n].pouvactif[p]=80; } else if (action == TERMINE) { if (perso[n].statut & INVISIBLE) { perso[n].statut ^= INVISIBLE; } if (perso[n].statut & FURIEDESTRUCTRICE) { perso[n].statut ^= FURIEDESTRUCTRICE; } } return; } void vitesse_f(int n, int p, int action) { int i, j, ncoul; int X, Y; int x, y; float f; float T=PI/4; float Ti=0; Coord pix[1000]; //x SDL_Rect tout={0, 0, 640, 480}; SDL_Rect tout={0, 0, resolution.window_width, resolution.window_height}; paletsg pal; SDL_Surface *contenu; #if 0 afficheperso(n, 0); x = perso[n].pos.x; /* (x et y servent à complètement autre chose après) */ y = perso[n].pos.y; if (plan.element[x][y].type == TUNNEL) { blitsprit(plan.element[x][y].elem, plan.element[x][y].anim, plan.element[x][y].frame, x*32, y*32); } dessinecase(ntunnel[nrs], rstunnel[nrs]); ntunnel[nrs]=0; #endif if (action == ACTIVATION) { ncoul = sprit[n]->decalage + sprit[n]->palette->ncolors; pal = changepalette(0.5, 0.7, 0, 8, sprit[n]->decalage, ncoul, ecran->format->palette->ncolors, 10); /* Tout devient marron */ contenu=SDL_DisplayFormat(ecran); //x X = perso[n].pixpos.x+16; X = resolution.x_offset+perso[n].pixpos.x+16; //x Y = perso[n].pixpos.y+16; Y = resolution.y_offset+perso[n].pixpos.y+16; for (i=0; i<1000; i++) { f = ((float)rand())/((float)RAND_MAX); /* nombre aleatoire entre 0 et 1 */ y = (int)(130.0*f); /* eloignement de l'origine */ x = aleat((int)(50.0*f)); /* ecartement de l'axe, proportionnel à f*/ pix[i].x = x*cos(f*PI)+y*sin(f*PI); /* rotation pour faire une spirale */ pix[i].y = y*cos(f*PI)-x*sin(f*PI); } for (i=0; i < 75; i++) { T *= 1.033; SDL_PumpEvents(); SDL_BlitSurface(contenu, &tout, ecran, &tout); SDL_LockSurface(ecran); for (Ti = 0; Ti < 2.0*PI; Ti += 2.0*PI/3.0) for (j=0; j < 1000; j++) { x = pix[j].x*cos(T+Ti)-pix[j].y*sin(T+Ti)+X; y = pix[j].y*cos(T+Ti)+pix[j].x*sin(T+Ti)+Y; //x if (0<=x && x<640 && 0<=y && y<480) if (0 <= x && x < resolution.window_width && 0 <= y && y < resolution.window_height) //x ((Uint8 *)ecran->pixels) [y*640+x] = sprit[n]->decalage+aleat(4)+4; ((Uint8 *)ecran->pixels) [y*resolution.window_width+x] = sprit[n]->decalage+aleat(4)+4; } SDL_UnlockSurface(ecran); SDL_Flip(ecran); } SDL_BlitSurface(contenu, &tout, ecran, &tout); if (dblebuf) { SDL_Flip(ecran); SDL_BlitSurface(contenu, &tout, ecran, &tout); } restorepalette(pal, 60); SDL_FreeSurface(contenu); perso[n].statut |= RAPIDE; perso[n].pouvactif[p]=500; } else if (action == TERMINE) { if (perso[n].statut & RAPIDE) { perso[n].statut ^= RAPIDE; } } return; } void passemur_f(int n, int p, int action) { if (action==ACTIVATION) { perso[n].statut |= PASSEMURAILLES|INVISIBLE; evtsplus(super, n, 0, 0, 0, 150, 0, APRES, NULL); perso[n].pouvactif[p]=150; } else if (action==TERMINE) { if (plan.element[perso[n].pos.x][perso[n].pos.y].type ==INDESTRUCTIBLE) mort(n, n); if (perso[n].statut & PASSEMURAILLES) perso[n].statut ^= PASSEMURAILLES; if (perso[n].statut & INVISIBLE) perso[n].statut ^= INVISIBLE; } return; } /*--Pouvoir par compteur--*/ void superbombes_f(int n, int p, int action) { if (action==ACTIVATION) { perso[n].pouvactif[p]=3; perso[n].statut |= SUPERBOMBE; } else if (action==TERMINE) { if (perso[n].statut & SUPERBOMBE) perso[n].statut ^= SUPERBOMBE; } return; } /*--Fonctions d'utilisation des pouvoirs--*/ void initpouv(int n) { int i; for (i=0; i<4; i++) { perso[n].pouv[i].f=NULL; perso[n].pouvactif[i]=0; } if (!strcmp(spritliste[n], "troll.spr")) { perso[n].pouv[0]=superbombes; perso[n].pouv[1]=vitesse; } if (!strcmp(spritliste[n], "trollb.spr")) { perso[n].pouv[0]=superbombes; perso[n].pouv[1]=invisible; } else if (!strcmp(spritliste[n], "magus.spr")) { perso[n].pouv[0]=bouclier; perso[n].pouv[1]=invisible; } else if (!strcmp(spritliste[n], "magusb.spr")) { perso[n].pouv[0]=bouclier; perso[n].pouv[1]=teleporte; } else if (!strcmp(spritliste[n], "barbare.spr")) { perso[n].pouv[0]=furie; perso[n].pouv[1]=bigexplosion; } else if (!strcmp(spritliste[n], "barbareb.spr")) { perso[n].pouv[0]=furie; perso[n].pouv[1]=vitesse; } else if (!strcmp(spritliste[n], "louis.spr")) { perso[n].pouv[0]=deguisement; perso[n].pouv[1]=teleporte; } else if (!strcmp(spritliste[n], "louisb.spr")) { perso[n].pouv[0]=deguisement; perso[n].pouv[1]=bigexplosion; } else if (!strcmp(spritliste[n], "citrouille.spr")) { perso[n].pouv[0]=plusdefeu; perso[n].pouv[1]=passemur; perso[n].pouv[2]=detonateur; perso[n].pouv[3]=touteteindre; } return; } void pouvoirplus(int n, int p, int coute) { if (perso[n].pouv[p].f==NULL) return; if (coute) { if (perso[n].pouv[p].energie > perso[n].energie) return; perso[n].energie-=perso[n].pouv[p].energie; bruitsplus(s_pouvoir, 1); } perso[n].pouvactif[p]=ACTIVATION; return; } void gerepouvoirs(void) { int i, j; for (i=0; iACTIVATION) { perso[i].pouvactif[j]-=ACTIVATION; perso[i].pouvactif[j]--; } if (!perso[i].pouvactif[j]) perso[i].pouv[j].f(i, j, TERMINE); } } } return; }