PageRenderTime 75ms CodeModel.GetById 9ms app.highlight 47ms RepoModel.GetById 10ms app.codeStats 1ms

/source/pintor.c

http://github.com/Vect/fail0verflow2
C | 1217 lines | 900 code | 185 blank | 132 comment | 210 complexity | 7081329c3e066f24038b966cc693a2ea MD5 | raw file
   1
   2/*  PINTOR for GP32
   3    Copyright (C) 2005  Hermes/PS2Reality 
   4
   5    This program is free software; you can redistribute it and/or modify
   6    it under the terms of the GNU General Public License as published by
   7    the Free Software Foundation; either version 2 of the License, or
   8    (at your option) any later version.
   9
  10    This program is distributed in the hope that it will be useful,
  11    but WITHOUT ANY WARRANTY; without even the implied warranty of
  12    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13    GNU General Public License for more details.
  14
  15    You should have received a copy of the GNU General Public License
  16    along with this program; if not, write to the Free Software
  17    Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
  18
  19*/
  20
  21#include <stdio.h>
  22#include <stdlib.h>
  23#include <string.h>
  24#include <math.h>
  25#include <time.h>
  26
  27#include <malloc.h>
  28#include <stdlib.h>
  29#include <unistd.h>
  30#include <sys/time.h>
  31#include "pad.h"
  32
  33#include "audioplayer.h"
  34#include "spu_soundlib.h"
  35
  36
  37#define WIDTH	256
  38#define HEIGHT	192
  39
  40#define BORDER	10
  41
  42static int pause_audio = 0;
  43
  44unsigned GetTicks()
  45{
  46 struct timeval tv;
  47    gettimeofday( &tv, 0 );
  48    
  49    return ((tv.tv_sec * 1000000) + tv.tv_usec) / 1000;
  50}
  51
  52
  53// VARIABLES DEL PROGRAMA
  54
  55
  56#define PAD_RIGHT BUTTON_RIGHT
  57#define PAD_LEFT BUTTON_LEFT
  58#define PAD_DOWN BUTTON_DOWN
  59#define PAD_UP BUTTON_UP
  60
  61
  62
  63int PADEVENT=0; // si 1 se puede leer el PAD
  64
  65
  66
  67/****************************************************************************************************************************************/
  68// PANTALLA
  69/****************************************************************************************************************************************/
  70
  71extern unsigned char msx[];  // define la fuente externa usada para dibujar letras y numeros 
  72unsigned *video=NULL;       // memoria que almacena la pantalla virtual
  73unsigned *video_text=NULL;  // memoria que almacena la textura
  74
  75#define SIZEVIDEO 4*256*192 // tama´┐Żo en bytes de la pantalla vir.
  76#define SCANVIDEO 256       // ancho de la pantalla vir.
  77#define DESPL8VID 11        // usado para ajustar Y a scans (se utilizan graficos de 8x8 pixeles, 8*SCANVIDEO=2048=2^11
  78#define ANCHO 32            // ancho de la pantalla en bloques de 8 pixeles
  79#define ALTO 24             // alto d ela pantalla en bloques de 8 pixeles
  80#define ALTO2 22            // se usa para presentar la puntuacion, vidas, etc en pantalla
  81
  82unsigned COLORFONDO=0x80804000; // color de fondo (vaya noticia :P)
  83
  84
  85
  86void ClearVideo(unsigned val) // se usa para 'borrar' la pantalla virtual con un color
  87{
  88int n;
  89for(n=0;n<SIZEVIDEO/4;n++)
  90	{
  91	video[n]=val;
  92	}
  93}
  94
  95extern void drawScene();
  96
  97void DrawScreen() // funcion evento que dibuja todos los elementos de la pantalla virtaul al LCD
  98{
  99    int n;
 100    unsigned c,c2;
 101    volatile unsigned *v;
 102
 103    c2=0xff00102f;
 104
 105    for(n = 0; n < (256 * 192); n++) {
 106	    v=((unsigned *) video) + n;
 107        c=(*v & 0xff00ff00) | ((*v<<16) & 0xff0000) | ((*v>>16) & 0xff);
 108        if(!c || c < 0x11000000) c = c2;
 109        video_text[n] = c;
 110    }  
 111    
 112    drawScene();
 113    ps3pad_read();PADEVENT=1;
 114}
 115
 116void v_putchar( unsigned x, unsigned y, unsigned color, unsigned char ch) // rutina usada para dibujar caracteres (coordenadas de 8x8)
 117{
 118   int 	i,j,v;
 119   unsigned char	*font;
 120  
 121   if(x>=ANCHO || y>=ALTO) return;
 122   v=(y<<DESPL8VID);
 123   font = &msx[ (int)ch * 8];
 124   for (i=0; i < 8; i++, font++)
 125		{  
 126		 for (j=0; j < 8; j++)
 127          {
 128          if ((*font & (128 >> j)))
 129			  { 
 130               video[v+(((x<<3)+j))]=color;
 131			  }
 132			else video[v+(((x<<3)+j))]=0;
 133          }
 134	  v+=SCANVIDEO;
 135	 }
 136 
 137}
 138
 139// display array of chars
 140
 141void v_putcad(int x,int y,unsigned color,char *cad)  // dibuja una cadena de texto
 142{
 143	
 144while(cad[0]!=0) {v_putchar(x,y,color,cad[0]);cad++;x++;}
 145}
 146
 147
 148/****************************************************************************************************************************************/
 149//  rutinas y definicion de UDG (User Defined Graphic) (8x8 pixeles)
 150/****************************************************************************************************************************************/
 151
 152// paleta de conversion de caracter/color
 153
 154unsigned PALETA[10]={0x0,0xff0000ff,0xff00ff00,0xff00ffff,0xffff0000,0xffff00ff,0xffffff00,0xffffffff,0xff000000,1};
 155
 156void SetUDG(unsigned x,unsigned y,unsigned char *punt) // dibuja un UDG
 157{
 158int n,m,v;
 159unsigned col;
 160if(x>=ANCHO || y>=ALTO) return;
 161v=(y<<DESPL8VID);
 162
 163for(n=0;n<8;n++)
 164	{
 165	for(m=0;m<8;m++)
 166		{
 167		col=(unsigned )*punt++;
 168		col-=48;
 169		col=PALETA[col];
 170		//if(col==1) col=COLORFONDO;
 171		if(col!=0)
 172        video[v+(((x<<3)+m))]=col;
 173		}
 174	v+=SCANVIDEO;
 175	}
 176}
 177
 178// lista de UDG's usados en el juego
 179unsigned char gdu_sprite[20][8][8]={
 180{
 181"33388333",
 182"33388333",
 183"33383383",
 184"38888833",
 185"83383333",
 186"33838833",
 187"33833833",
 188"38333383",
 189},
 190{
 191"99999999",
 192"99999999",
 193"99999999",
 194"99999999",
 195"99999999",
 196"99999999",
 197"99999999",
 198"99999999",
 199},
 200{
 201"77777777",
 202"77777777",
 203"77777777",
 204"77777777",
 205"77777777",
 206"77777777",
 207"77777777",
 208"77777777",
 209},
 210{
 211"33333333",
 212"33333333",
 213"33333333",
 214"33333333",
 215"33333333",
 216"33333333",
 217"33333333",
 218"33333333",
 219},
 220{
 221"33388333",
 222"33388333",
 223"38338333",
 224"33888883",
 225"33338338",
 226"33883833",
 227"33833833",
 228"38333383",
 229},
 230{
 231"22222222",
 232"22222222",
 233"22222222",
 234"22222222",
 235"22222222",
 236"22222222",
 237"22222222",
 238"22222222",
 239},
 240{
 241// 6
 242"00001100",
 243"10111110",
 244"11111011",
 245"01111111",
 246"01111000",
 247"00110111",
 248"00111110",
 249"00001100",
 250},
 251{
 252"00001100",
 253"00111110",
 254"01111011",
 255"01111111",
 256"01111000",
 257"11110001",
 258"10111110",
 259"00001100",
 260},
 261{
 262
 263// 8
 264"00110000",
 265"01111101",
 266"11011111",
 267"11111110",
 268"00011110",
 269"11101100",
 270"01111100",
 271"00110000",
 272
 273},
 274{
 275"00110000",
 276"01111100",
 277"11011110",
 278"11111110",
 279"00011110",
 280"10001111",
 281"01111101",
 282"00110000",
 283},
 284
 285
 286};
 287
 288
 289/****************************************************************************************************************************************/
 290// definicion de mapas del juego
 291/****************************************************************************************************************************************/
 292
 293
 294// definicion d elos mapas: A,B,C,D->representa donde aparecen los bichos, 1,2->caminos
 295unsigned char map_screens[8][22][32]={
 296
 297{
 298////////////////////////////////////
 299"            2      2            ",
 300"             2    2             ",
 301"                                ",
 302"            22222222            ",
 303"                                ",
 304"11111111111                     ",
 305" 1        11                    ",
 306" 1         1     1              ",
 307" 1        11     1              ",
 308" 1111111111   111111111         ",
 309" 1               1          1 11",
 310" 1  2    1 11111 1    1111  111 ",
 311" 1       111   1 1   11  11 1   ",
 312" 1  1    1     111   1    1 1   ",
 313" 1111    1     1 1   1    111   ",
 314" 1  1    1     1 1   1    1 1   ",
 315" 1  11   1     1 11  11  11 1   ",
 316" A   1111D     1  11B11111  C   ",
 317"                                ",
 318"22222222222222222222222222222222",
 319"22222222222222222222222222222222",
 320"                                ",
 321},
 322{
 323//////////////////////////////////
 324"A1111111                1111111D",
 325"1      1                1      1",
 326"1      11111111$111111111      1",
 327"1      1                1      1",
 328"1      1                1      1",
 329"1      111111111111111111      1",
 330"1      1    1      1    1      1",
 331"11111111    1      1    11111111",
 332"  1  1    111111111111    1  1  ",
 333"  1  1    1          1    1  1  ",
 334"  1  1    1          1    1  1  ",
 335"  1  1    1          1    1  1  ",
 336"  1  1    1          1    1  1  ",
 337"  1  1    111111111111    1  1  ",
 338"11111111    1      1    11111111",
 339"1      1    1      1    1      1",
 340"1      111111111111111111      1",
 341"1      1                1      1",
 342"1      1                1      1",
 343"1      111111111111111111      1",
 344"1      1                1      1",
 345"C1111111                1111111B",
 346},
 347{
 348////////////////////////////////////
 349"   A11111              11111D   ",
 350"   1    1              1    1   ",
 351"111111111111        111111111111",
 352"1          1        1          1",
 353"1          1        1          1",
 354"111111111111        111111111111",
 355"   1    1   11111111   1    1   ",
 356"   1    1   1      1   1    1   ",
 357"   1    1   1      1   1    1   ",
 358"1111111111111111$111111111111111",
 359"1                              1",
 360"1                              1",
 361"1                              1",
 362"11111111111111111111111111111111",
 363"   1        1      1        1   ",
 364"   1        1      1        1   ",
 365"   1        1      1        1   ",
 366"   1        1      1        1   ",
 367"   1        1      1        1   ",
 368"   C111111111      111111111B   ",
 369"                                ",
 370"                                ",
 371////////////////////////////////////
 372},
 373{
 374////////////////////////////////////
 375"A1111                11111      ",
 376"1   1                1   1      ",
 377"1   1                1   1      ",
 378"1   111111111111111111111111111D",
 379"1   1                1   1     1",
 380"1   1                1   1     1",
 381"1   1111111111111$11111111111111",
 382"1   1                1   1      ",
 383"1   1                1   1      ",
 384"1   1         1111111111111111  ",
 385"1   1         1              1  ",
 386"1   1         1              1  ",
 387"1   1         1              1  ",
 388"1   1   111111111111111111111111",
 389"1   1   1                      1",
 390"1   1   1                      1",
 391"1   1111111111111111111111111111",
 392"1   1                       1   ",
 393"1   1                       1   ",
 394"1   111111111111111111111111B   ",
 395"1   1    1            1         ",
 396"C1111    11111111111111         ",
 397},
 398{
 399////////////////////////////////////
 400"    A11111      111111111111D   ",
 401"    1    1      1           1   ",
 402" 111111111  11111111111111111111",
 403" 1       1  1      1      1    1",
 404" 1       1  1      1      1    1",
 405" 111111111  1      1      1    1",
 406"    1    1  1      1      1    1",
 407"    1    1  1      1      1    1",
 408"    1    1  1      1111111111111",
 409"    1    1  1      1           1",
 410"    1    1  1      1           1",
 411"    1    1  1      1           1",
 412"    1    1  1111$111111111111111",
 413"    1    1  1      1      1    1",
 414"    1    1  1      1      1    1",
 415"    1    1  1      1      1    1",
 416"    1    1  1      1      1    1",
 417"11111111111111111111111111111111",
 418"1                            1  ",
 419"1                            1  ",
 420"1                            1  ",
 421"C1111111111111111111111111111B  ",
 422////////////////////////////////////
 423},
 424{
 425////////////////////////////////////
 426"A11111111   11111111   11111111D",
 427"1       1   1      1   1       1",
 428"1       1   1      1   1       1",
 429"1       1 111111111111 1       1",
 430"111111111 1          1 111111111",
 431"    1     1          1     1    ",
 432"1111111111111111$111111111111111",
 433"1         1          1         1",
 434"1         1          1         1",
 435"1         1          1         1",
 436"1         111111111111         1",
 437"1         1  1    1  1         1",
 438"1         1  1    1  1         1",
 439"11111111111  1    1  11111111111",
 440"  1     1    1    1    1     1  ",
 441"  1     1111111111111111     1  ",
 442"  1     1              1     1  ",
 443"  1     1              1     1  ",
 444"11111111111111111111111111111111",
 445"1          1        1          1",
 446"1          1        1          1",
 447"C11111111111        11111111111B",
 448////////////////////////////////////
 449},
 450{
 451////////////////////////////////////
 452"                                ",
 453"                                ",
 454"                                ",
 455"                                ",
 456"                                ",
 457"                                ",
 458"                                ",
 459"                                ",
 460"                                ",
 461"                                ",
 462"                                ",
 463"                                ",
 464"                                ",
 465"                                ",
 466"                                ",
 467"                                ",
 468"                                ",
 469"                                ",
 470"                                ",
 471"                                ",
 472"                                ",
 473"                                ",
 474////////////////////////////////////
 475},
 476
 477
 478};
 479// numero de anillos por mapa
 480int map_screen_rings[10]={66,11,10,10,12,13,0,0,0,0};
 481
 482/****************************************************************************************************************************************/
 483// variables del juego
 484/****************************************************************************************************************************************/
 485
 486
 487int pausa=0; // 1- juego pausado
 488
 489unsigned puntos=0; // si te tengo que explicar esto, mejor lo dejamos :P
 490unsigned hiscore=0;
 491int vidas=3;
 492int nbichos=2;
 493
 494int rings=0; // anillos completados
 495unsigned protadir=0; // para donde miramos
 496int bichodir[4]={0,0,0,0}; // para donde miran los bichos
 497
 498int ACTMAP=0; // mapa actual
 499unsigned char map_screen[24][32]; // aqui se trabaja (se copia el mapa aqui para ello)
 500
 501
 502//  control de eventos de sonido
 503int message_scroll=0;
 504int message_effect1=0;
 505int message_effect2=0;
 506int message_camina[4]={0,0,0,0};
 507int piok=0;
 508int message_piok=0; // me han 'picado' me temo :D
 509
 510/****************************************************************************************************************************************/
 511// manejo y control de mapas del juego
 512/****************************************************************************************************************************************/
 513
 514
 515void copyMAP()
 516{
 517int n,m;
 518unsigned char c;
 519protadir=0;
 520
 521rings=0;
 522piok=0;
 523message_piok=0;
 524for(n=0;n<4;n++) 
 525	{bichodir[n]=0;
 526    message_camina[n]=0;
 527    }
 528 message_effect2=0;
 529message_effect1=0;
 530message_scroll=0;
 531ClearVideo(0);
 532
 533switch(ACTMAP)
 534	{
 535	case 0:COLORFONDO=0x80800000;PALETA[2]=0x80ff8000;break;
 536	case 2:COLORFONDO=0x80004020;PALETA[2]=0x8000ff80;break;
 537	case 3:COLORFONDO=0x80404040;PALETA[2]=0x808000ff;break;
 538	case 4:COLORFONDO=0x80404000;PALETA[2]=0x8000ff00;break;
 539	case 5:COLORFONDO=0x80402040;PALETA[2]=0x80ff00ff;break;
 540	default:COLORFONDO=0x80804000;PALETA[2]=0x80ff8000;
 541	}
 542
 543//memcpy(map_screen,&map_screens[ACTMAP][0][0],32*22);
 544for(n=0;n<22;n++)
 545{
 546for(m=0;m<32;m++)
 547	{
 548    c=map_screens[ACTMAP][n][m];
 549    // esto sucede la primera vez
 550	if(c==' ') c=0;
 551	else
 552	if(c=='1') c=1;
 553	else
 554	if(c=='2') c=2;
 555	else
 556	if(c=='$') c=130;
 557	else
 558	if(c=='A') c=65;
 559	else
 560	if(c=='B' && nbichos>1) c=33;
 561    else
 562	if(c=='C' && nbichos>2) c=17;
 563    else
 564	if(c=='D' && nbichos>3) c=9;
 565	else c=1;
 566	map_screen[n][m]=c;
 567	}
 568}
 569}
 570
 571int AnalizeMAP();
 572
 573void scrollMAP() // efecto de scroll lateral de cuando completamos un mapa
 574{
 575int n,m;
 576
 577for(n=0;n<22;n++)
 578	{
 579	for(m=30;m>=0;m--)
 580		{
 581		map_screen[n][m+1]=map_screen[n][m];
 582		}
 583	map_screen[n][0]=0;
 584	}
 585}
 586
 587static int screen_count0 = 0;
 588
 589void DrawMAP() // dibuja el mapa y actualiza variables
 590{
 591int n,m,v;
 592unsigned char c;
 593char cad[256];
 594static int paso=0,count=0,count2=0;
 595
 596
 597
 598screen_count0++;
 599
 600count2++;
 601if(count2>=50) {count2=0;}
 602count++;
 603if(count>=32){count=0;paso^=1;}
 604
 605
 606if(rings>=map_screen_rings[ACTMAP] || piok || pausa || ACTMAP==0) count2=20; // evita efectos de sonido
 607else
 608rings+=AnalizeMAP();
 609//if(rings>map_screen_rings[ACTMAP]) return ; // si se han comppletado los anillos retorna
 610
 611for(n=0;n<22;n++)
 612{
 613for(m=0;m<32;m++)
 614	{
 615    c=map_screen[n][m];
 616    // esto sucede la primera vez
 617	/*if(c=='$') {c='2' | 128;map_screen[n][m]=c; }
 618	if(c=='A') {c='1' | 128;map_screen[n][m]=c; }*/
 619	// pinta fondo mapa
 620	
 621	v=(c & 7)+1;
 622	
 623	SetUDG(m,n,(unsigned char *) &gdu_sprite[v][0][0]);
 624	// mi personaje esta aqui?
 625	if(c & 128) {if((c & 120) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}SetUDG(m,n,(unsigned char *) &gdu_sprite[4*(protadir==1 || protadir==4)][0][0]);c=(c & 0xfc) | 130;map_screen[n][m]=c;}
 626	// veo bichos!!
 627	if(c & 64) {if((c & 128) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 628		       if(count2==0) message_camina[0]=(m-16)+(m==16);SetUDG(m,n,(unsigned char *) &gdu_sprite[6+paso+2*(bichodir[0]==1 || bichodir[0]==4)][0][0]);}
 629	if(c & 32) {if((c & 128) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 630		       if(count2==0) message_camina[1]=(m-16)+(m==16);SetUDG(m,n,(unsigned char *) &gdu_sprite[6+paso+2*(bichodir[1]==1 || bichodir[1]==4)][0][0]);}
 631	if(c & 16) {if((c & 128) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 632		       if(count2==0) message_camina[2]=(m-16)+(m==16);SetUDG(m,n,(unsigned char *) &gdu_sprite[6+paso+2*(bichodir[2]==1 || bichodir[2]==4)][0][0]);}
 633	if(c & 8) {if((c & 128) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 634		      if(count2==0) message_camina[3]=(m-16)+(m==16);SetUDG(m,n,(unsigned char *) &gdu_sprite[6+paso+2*(bichodir[3]==1 || bichodir[3]==4)][0][0]);}
 635	}
 636}
 637
 638
 639if(ACTMAP!=0) // si no es pantalla 0
 640{if(puntos>hiscore) hiscore=puntos;
 641sprintf(cad,"SCORE:%6.6u HI:%6.6u ",puntos,hiscore); 
 642v_putcad(0,23,0xffffFFff,cad);
 643v_putcad(23,23,0xffffFFff,"LIVES:");
 644for(n=0;n<vidas;n++) SetUDG(29+n,23,(unsigned char *) &gdu_sprite[0]);
 645screen_count0 = 0;
 646}
 647else
 648{
 649
 650if(screen_count0<30)
 651    {
 652    v_putcad(7,22,0xffffffff,"by HermesEOL / 2011");
 653    v_putcad(6,23,0xffffffff,"Fail0verflow Version");
 654    }
 655else
 656    {
 657
 658    memset(video, 0, SIZEVIDEO);
 659    v_putcad(11, 1,0xff00ffff,"Starring:");
 660
 661    SetUDG(3,3,(unsigned char *) &gdu_sprite[0]);
 662    v_putcad(4, 3,0xffffffff,"..... 1 to 100 John Does");
 663
 664    SetUDG(3,5,(unsigned char *) &gdu_sprite[8]);
 665    v_putcad(4, 5,0xffffffff,"..... Giant Crab S.C.E.A.");
 666
 667    SetUDG(3,7,(unsigned char *) &gdu_sprite[9]);
 668    v_putcad(4, 7,0xffffffff,"..... Attorneys lapdogs");
 669
 670    v_putcad(13, 9,0xff00ffff,"Music:");
 671
 672    v_putcad(0, 11,0xffffffff,"The Light It Up Contest-Geohot");
 673
 674    v_putcad(11, 13,0xff00ffff,"No Thanks:");
 675
 676    v_putcad(0, 15,0xffffffff,"To github to erase the original");
 677    v_putcad(0, 16,0xffffffff,"fail0verflow repository cowardly ");
 678    v_putcad(0, 17,0xffffffff,"without any reason to justify it.");
 679    
 680    v_putcad(7,22,0xffffffff,"by HermesEOL / 2011");
 681    v_putcad(6,23,0xffffffff,"Fail0verflow Version");
 682
 683    if(screen_count0>60) screen_count0 = 0;
 684    }
 685    
 686}
 687
 688}
 689
 690int subanalizeMAP(int x,int y) // llamada por analizeMAP(), me gustan los nombres rarus
 691{
 692int n,m;
 693
 694int xx1,yy1,xx2,yy2;
 695
 696if(x>29 || y>19) return 0;
 697if((map_screen[y][x+1] & 3)!=2 || (map_screen[y+1][x] & 3)!=2) return 0;
 698
 699xx1=xx2=x;yy1=yy2=y;
 700// busca una bifurcacion hacia abajo
 701for(m=x+1;m<32;m++)
 702	{
 703	if((map_screen[y][m] & 3)==2)
 704	{
 705	if((map_screen[y+1][m] & 3)==1) break;
 706	if((map_screen[y+1][m] & 3)==2) {xx2=m;break;}
 707	} else break;
 708	}
 709// busca una bifurcacion a la derecha
 710for(m=y+1;m<22;m++)
 711	{
 712	if((map_screen[m][x] & 3)==2)
 713	{
 714	if((map_screen[m][x+1] & 3)==1) break; 
 715	if((map_screen[m][x+1] & 3)==2) {yy2=m;break;}
 716	} else break;
 717	}
 718if(xx1==xx2 || yy1==yy2) return 0;
 719
 720for(m=xx1;m<=xx2;m++)
 721	{
 722	if((map_screen[yy2][m] & 3)!=2) break;
 723	}
 724if(m<=xx2) return 0; // no esta completo el circulo
 725for(m=yy1;m<=yy2;m++)
 726	{
 727	if((map_screen[m][xx2] & 3)!=2) break;
 728	}
 729if(m<=yy2) return 0; // no esta completo el circulo
 730// recuadro a iluminar
 731for(n=yy1+1;n<yy2;n++)
 732	{
 733	for(m=xx1+1;m<xx2;m++)
 734		{
 735		if(map_screen[n][m]==4) return 0; // ya estaba pintado
 736		map_screen[n][m]=4;
 737		}
 738	}
 739message_effect1=1; // emite un sonido
 740return 1;
 741}
 742
 743int AnalizeMAP() // rutina que sirve para que el programa se entere de lo que pasa en el mapa (busca anillos)
 744{
 745int numrec=0;
 746int n,m;
 747
 748for(n=0;n<22;n++)
 749{
 750for(m=0;m<32;m++)
 751	{
 752	if((map_screen[n][m] & 3)==2)  
 753		{
 754		if(subanalizeMAP(m,n)) numrec++;
 755		}
 756	}
 757}
 758puntos+=10*numrec*nbichos;
 759return numrec;
 760}
 761
 762void Borra_Prota()
 763{
 764int n,m;
 765for(n=0;n<22;n++)
 766{
 767for(m=0;m<32;m++)
 768	{
 769    map_screen[n][m]&=127;
 770	}
 771}
 772}
 773
 774void Move_Bicho(unsigned nbi) // mola el spanglish :D
 775{
 776int n,m;
 777unsigned char c,mask,mask2;
 778int testmove=0,contmove=0;
 779switch(nbi)
 780{
 781case 1: mask=32;mask2=255-32;break;
 782case 2: mask=16;mask2=255-16;break;
 783case 3: mask=8;mask2=255-8;break;
 784default: mask=64;mask2=255-64;
 785}
 786//busca al bichin :P
 787for(n=0;n<22;n++)
 788{
 789for(m=0;m<32;m++)
 790	{
 791    c=map_screen[n][m];
 792	if(c & mask) // detectado bicho
 793		{
 794		do
 795		{
 796		if(bichodir[nbi]==0)
 797			{bichodir[nbi]=(rand() & 1)+1; message_effect2=1;}
 798         if(bichodir[nbi]==1 || bichodir[nbi]==2)
 799			{
 800			if(n>0) if(map_screen[n-1][m] & 3) if((rand() & 15)<4) {bichodir[nbi]=4;message_effect2=1;} 
 801			if(n<21) if(map_screen[n+1][m] & 3) if((rand() & 15)<4) {bichodir[nbi]=8;message_effect2=1;} 
 802			}
 803         else
 804			{
 805			{
 806			if(m>0) if(map_screen[n][m-1] & 3) if((rand() & 15)<4) {bichodir[nbi]=1;message_effect2=1;} 
 807			if(m<31) if(map_screen[n][m+1] & 3) if((rand() & 15)<4) {bichodir[nbi]=2;message_effect2=1;}
 808			}
 809			}
 810		if(bichodir[nbi] & 1)
 811			{
 812			if(m>0) if(map_screen[n][m-1] & 3) {map_screen[n][m]&=mask2;map_screen[n][m-1]|=mask;testmove++;}
 813			}
 814		else
 815		if(bichodir[nbi] & 2)
 816			{
 817			if(m<31) if(map_screen[n][m+1] & 3) {map_screen[n][m]&=mask2;map_screen[n][m+1]|=mask;testmove++;}
 818			}
 819		else
 820		if(bichodir[nbi] & 4)
 821			{
 822			if(n>0) if(map_screen[n-1][m] & 3) {map_screen[n][m]&=mask2;map_screen[n-1][m]|=mask;testmove++;}
 823			}
 824		else
 825		if(bichodir[nbi] & 8)
 826			{
 827			if(n<21) if(map_screen[n+1][m] & 3) {map_screen[n][m]&=mask2;map_screen[n+1][m]|=mask;testmove++;}
 828			}
 829		contmove++;
 830		if(contmove>32 && testmove==0) { // anticuelgue
 831			           contmove=0;
 832					   bichodir[nbi]=0;
 833						}
 834		}while(testmove==0);
 835	if((c & 128) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 836	return;
 837		}
 838		
 839	}
 840}
 841
 842}
 843
 844
 845void Move_Prota(unsigned pad)
 846{
 847int n,m;
 848unsigned char c;
 849for(n=0;n<nbichos;n++) Move_Bicho(n);
 850
 851//busca a mi personaje
 852for(n=0;n<22;n++)
 853{
 854for(m=0;m<32;m++)
 855	{
 856    c=map_screen[n][m];
 857	if(c & 128) // detectado protagonista
 858		{
 859		if((c & 120) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 860		if((pad & PAD_LEFT) && protadir!=1)
 861			{
 862			if(m>0) if(map_screen[n][m-1] & 3) protadir=1;
 863			}
 864		else
 865	    if((pad & PAD_RIGHT) && protadir!=2)
 866			{
 867			if(m<31) if(map_screen[n][m+1] & 3)protadir=/*(protadir  & 12) |*/ 2;
 868			}	
 869		else
 870       if((pad & PAD_UP) && protadir!=4)
 871			{
 872			if(n>0) if(map_screen[n-1][m] & 3)protadir=/*(protadir  & 3) |*/ 4;
 873			}
 874		else
 875	    if((pad & PAD_DOWN) && protadir!=8)
 876			{
 877			if(n<21) if(map_screen[n+1][m] & 3) protadir=/*(protadir  & 3) |*/ 8;
 878			}	
 879			
 880
 881//protadir=1;
 882		if(protadir & 1)
 883			{
 884			if(m>0) if(map_screen[n][m-1] & 3) {map_screen[n][m]&=127;map_screen[n][m-1]=(map_screen[n][m-1] & 0xfc) | 130;}
 885			}
 886		else
 887		if(protadir & 2)
 888			{
 889			if(m<31) if(map_screen[n][m+1] & 3) {map_screen[n][m]&=127;map_screen[n][m+1]=(map_screen[n][m+1] & 0xfc) | 130;}
 890			}
 891		else
 892		if(protadir & 4)
 893			{
 894			if(n>0) if(map_screen[n-1][m] & 3) {map_screen[n][m]&=127;map_screen[n-1][m]=(map_screen[n-1][m] & 0xfc) | 130;}
 895			}
 896		else
 897		if(protadir & 8)
 898			{
 899			if(n<21) if(map_screen[n+1][m] & 3) {map_screen[n][m]&=127;map_screen[n+1][m]=(map_screen[n+1][m] & 0xfc) | 130;}
 900			}
 901	if((c & 120) && piok==0){piok=16384+(n<<5)+m;message_piok=1;}
 902	return;
 903		}
 904		
 905	}
 906}
 907
 908}
 909
 910
 911/****************************************************************************************************************************************/
 912//  SONIDO (generaci´┐Żn)
 913/****************************************************************************************************************************************/
 914
 915
 916
 917int time1_sound=0;
 918int time2_sound=0;
 919int time3_sound=0;
 920int time4_sound=0;
 921int count_sound=0;
 922int count2_sound=0;
 923int vol_sound=0;
 924int mod_sound=1;
 925
 926/* set_sonido
 927vol=volumen (0-0x7fff)
 928hz=frecuencia en hz del sonido
 929time_on=tiempo en ms que se reproduce la onda
 930time_off=tiempo en ms deonda en off (intermitencia)
 931times=numero de veces que se repite (-1=infinito)
 932*/
 933
 934void set_sonido(int vol,int hz,int time_on,int time_off,int times) // programa un sonido
 935{
 936int a;
 937time4_sound=0;
 938//time_on>>=1;
 939//time_off>>=1;
 940vol_sound=vol;
 941a=44100/hz;
 942if(a==0) a=2;
 943time1_sound=a;
 944time_on=(11025*time_on)/(a*1000);
 945if(time_on==0) time_on=1;
 946time2_sound=time_on;
 947time3_sound=(11025*time_off)/1000;
 948time4_sound=times;
 949
 950}
 951
 952// mezclador de audio de las SDL llamado como eventos
 953
 954void mixaudio(void *unused, u8 *stream, int len)
 955{
 956
 957int n;
 958
 959int mid;
 960short *pu;
 961mid=time1_sound>>1;
 962pu=(short *) stream;
 963for(n=0;n<(len>>2);n++)
 964	{
 965	if(time4_sound!=0)
 966		{
 967		if(count2_sound<time2_sound)
 968			{
 969			if(count_sound==mid) {pu[0]=pu[1]=0;pu+=2;} else 
 970			if(count_sound<mid) {pu[0]=pu[1]=vol_sound;pu+=2;} else {pu[0]=pu[1]=-vol_sound;pu+=2;}
 971			count_sound++;if(count_sound>=time1_sound) {count_sound=0;count2_sound++;}
 972			}
 973		else
 974			{
 975			if(count_sound<time3_sound) {pu[0]=pu[1]=0;pu+=2;count_sound++;} 
 976			else {count_sound=count2_sound=0;if(time4_sound>0) time4_sound--;}
 977			}
 978		}
 979	}
 980
 981}
 982   
 983
 984/****************************************************************************************************************************************/
 985//  MAIN
 986/****************************************************************************************************************************************/
 987
 988unsigned oldtime=0; // se usa para conocer el tiempo transcurrido en ms
 989int count20ms=0; // variable rara vinculada al temporizador
 990
 991//int temp_keys,new_keys=0,old_keys=0; // usadas para leer el pad 
 992
 993static short pcmout[2][2048];
 994int pcm_flip=0;
 995
 996static void audio_add_callback(int voice)
 997{
 998	if(SND_TestVoiceBufferReady(1)==1)
 999	{
1000	//void mixaudio(void *unused, u8 *stream, int len)
1001	mixaudio(NULL,  (void *) &pcmout[pcm_flip][0],2048);
1002	if(SND_AddVoice(1, (void *) &pcmout[pcm_flip][0],2048)==0) 
1003		{
1004		pcm_flip^=1;
1005		}
1006	}
1007}
1008
1009
1010
1011int pintor()
1012{
1013
1014unsigned time1,n;
1015    
1016
1017video=malloc(SIZEVIDEO);
1018//video_text=memalign(32,WIDTH*HEIGHT*4);
1019
1020SND_SetVoice(1, VOICE_STEREO_16BIT, 11025*2,0, (void *) &pcmout[pcm_flip][0], 2048, 63, 63, audio_add_callback);
1021pcm_flip^=1;
1022
1023
1024
1025/////////////////////////////////////////////////////////////
1026do
1027{
1028ACTMAP=0;
1029vidas=3;
1030puntos=0;
1031pausa=0;
1032
1033do
1034{
1035copyMAP();
1036
1037new_pad=old_pad=0;
1038
1039while(1==1) // bucle principal donde se desarrolla toda la accion :O
1040{
1041
1042if(!time4_sound && !pausa) 
1043	{if(message_effect1) {mod_sound=0;message_effect1=0; set_sonido(127<<8,1200,125,0,1);}
1044	 else
1045	if(message_effect2) {mod_sound=1;message_effect2=0; set_sonido((63<<8),300,75,125,1);}
1046       else /*if(message_effect1)*/ {mod_sound=1;message_effect1=0;  set_sonido((32<<8),150,60,125,1);}
1047	}
1048
1049if(rings>=map_screen_rings[ACTMAP]) break; // pasa a sigueinte pantalla
1050
1051		
1052if(PADEVENT) 
1053	    {
1054		PADEVENT=0; // anula el evento (lectura cada 20ms, recuerda)
1055        
1056        #define J_DEATHZ 64 // death zone for sticks
1057
1058        if(pad_alive)
1059            {
1060		    if(paddata.ANA_R_V > (127+J_DEATHZ)) old_pad|=BUTTON_DOWN;
1061            if(paddata.ANA_R_V < (127-J_DEATHZ)) old_pad|=BUTTON_UP;
1062            if(paddata.ANA_L_V > (127+J_DEATHZ)) old_pad|=BUTTON_DOWN;
1063            if(paddata.ANA_L_V < (127-J_DEATHZ)) old_pad|=BUTTON_UP;
1064
1065            if(paddata.ANA_R_H > (127+J_DEATHZ)) old_pad|=BUTTON_RIGHT;
1066            if(paddata.ANA_R_H < (127-J_DEATHZ)) old_pad|=BUTTON_LEFT;
1067            if(paddata.ANA_L_H > (127+J_DEATHZ)) old_pad|=BUTTON_RIGHT;
1068            if(paddata.ANA_L_H < (127-J_DEATHZ)) old_pad|=BUTTON_LEFT;
1069
1070            pad_alive = 0;
1071            }
1072
1073        /*
1074
1075		if(wmote_datas!=NULL && wmote_datas->exp.type==WPAD_EXP_CLASSIC)
1076			{
1077 
1078			if(temp_pad & WPAD_CLASSIC_BUTTON_UP) temp_pad|=BUTTON_RIGHT;
1079
1080			if(temp_pad & WPAD_CLASSIC_BUTTON_DOWN) temp_pad|=BUTTON_LEFT;
1081		
1082			if(temp_pad & WPAD_CLASSIC_BUTTON_LEFT) temp_pad|=BUTTON_UP;
1083
1084			if(temp_pad & WPAD_CLASSIC_BUTTON_RIGHT) temp_pad|=BUTTON_DOWN;
1085			
1086			if(new_pad & WPAD_CLASSIC_BUTTON_A) new_pad|=BUTTON_CROSS;
1087			if(old_pad & WPAD_CLASSIC_BUTTON_A) old_pad|=BUTTON_CROSS;
1088
1089			if(new_pad & WPAD_CLASSIC_BUTTON_B) new_pad|=WPAD_BUTTON_B;
1090			if(old_pad & WPAD_CLASSIC_BUTTON_B) old_pad|=WPAD_BUTTON_B;
1091
1092			if(new_pad & WPAD_CLASSIC_BUTTON_X) new_pad|=WPAD_BUTTON_1;
1093			if(old_pad & WPAD_CLASSIC_BUTTON_X) old_pad|=WPAD_BUTTON_1;
1094
1095			if(new_pad & WPAD_CLASSIC_BUTTON_Y) new_pad|=WPAD_BUTTON_2;
1096			if(old_pad & WPAD_CLASSIC_BUTTON_Y) old_pad|=WPAD_BUTTON_2;
1097
1098			if(new_pad & WPAD_CLASSIC_BUTTON_HOME) new_pad|=BUTTON_START;
1099			if(old_pad & WPAD_CLASSIC_BUTTON_HOME) old_pad|=WPAD_BUTTON_HOME;
1100			}
1101        */
1102        
1103        if(new_pad & BUTTON_START) {goto sal_del_juego;}
1104
1105        if((new_pad & BUTTON_SQUARE)) {pause_audio^=1;PauseAudio(pause_audio);}
1106		
1107		if(ACTMAP==0)
1108		{
1109		if((new_pad & BUTTON_CROSS)) {pausa=0;rings=500;screen_count0 = -128;} // empieza
1110		// ajusta bichos
1111		if(new_pad & (BUTTON_UP)) {nbichos--;if(nbichos<2) nbichos=2;copyMAP();}
1112		if(new_pad & (BUTTON_DOWN)) {nbichos++;if(nbichos>4) nbichos=4;copyMAP();}
1113		}
1114		// pausa
1115		
1116		if(new_pad & BUTTON_SELECT) pausa^=1;
1117		
1118        
1119		 
1120		 }
1121time1=GetTicks();
1122count20ms=(time1-oldtime)/20;
1123//if(count20ms & 1) {
1124/*if(PADEVENT==0) 
1125	{
1126
1127	
1128	
1129	PADEVENT=1;}
1130//	}
1131*/
1132//if(pausa) count20ms=0;
1133
1134if(count20ms>8 || pausa)
1135	{
1136	oldtime=time1;
1137	
1138	if(!pausa) Move_Prota(old_pad);DrawMAP();DrawScreen();
1139	count20ms=0;
1140	}
1141
1142if(piok) break;
1143}
1144n=0;
1145if(piok==0) 
1146{ // rutina fin de pantalla
1147message_scroll=1;
1148set_sonido(127<<8,200,100,100,-1);mod_sound=0;
1149//n=100;
1150while(n<36)
1151	{
1152	time1=GetTicks();
1153	count20ms=(time1-oldtime)/20;
1154	
1155	if(count20ms>2)
1156	{
1157	oldtime=time1;
1158	n++;scrollMAP();
1159	count20ms=0;
1160	}
1161	
1162	
1163	DrawMAP();DrawScreen();
1164	}
1165	
1166ACTMAP++;mod_sound=1;time4_sound=0;
1167}
1168else
1169	{ 
1170		 
1171	Borra_Prota();
1172	mod_sound=0;
1173
1174	while(n<26)
1175	{
1176
1177	
1178	time1=GetTicks();   
1179	count20ms=(time1-oldtime)/20;
1180	
1181	if(count20ms>2)
1182	{
1183	n++;set_sonido(127<<8,1900-300*n/26,50,0,1);
1184
1185	oldtime=time1;
1186    map_screen[(piok>>5) & 31][piok & 31]&=127;
1187    if(((piok>>5) & 31)<21)
1188		{
1189		piok+=32;
1190		map_screen[(piok>>5) & 31][piok & 31]&=0xf8;
1191		map_screen[(piok>>5) & 31][piok & 31]|=130;
1192		}
1193	count20ms=0;
1194	}
1195	
1196	DrawMAP();DrawScreen();
1197	}
1198	mod_sound=1;time4_sound=0;
1199	
1200    vidas--;
1201	}
1202	
1203if(vidas<=0) break;
1204
1205if(map_screen_rings[ACTMAP]==0) ACTMAP=1;
1206}while(map_screen_rings[ACTMAP]!=0);
1207
1208}while(1);
1209
1210sal_del_juego:
1211
1212SND_StopVoice(1);
1213if(video) free(video); video=NULL;
1214//if(video_text) free(video_text); video_text=NULL;
1215
1216return 0;
1217}