Partage
  • Partager sur Facebook
  • Partager sur Twitter

[FAIT][Défis] #2 : Le jeu de la vie !

SDL

    12 septembre 2011 à 14:50:58

    Il me semble qu'il faut utiliser 2 tableaux.
    C'est ce que j'ai fait en tout cas. :-°
    • Partager sur Facebook
    • Partager sur Twitter
    Zeste de Savoir, le site qui en a dans le citron !
      12 septembre 2011 à 14:51:08

      Logiquement, aucun ordre n'est donné, donc c'est par génération.
      • Partager sur Facebook
      • Partager sur Twitter
        12 septembre 2011 à 14:55:50

        Hahaha excellent le U, en fait c'est la combinaison de base à mettre par défaut pour vendre le projet ^^

        J'vais peut être m'y mettre j'pense.

        Et j'avoue m'être posé la même question que Pampattitude.
        Moi je vois ça dans deux tableaux pareil.
        • Partager sur Facebook
        • Partager sur Twitter
          12 septembre 2011 à 17:48:07

          salut,
          honnêtement, je suis assez impressionné par la vitesse des réponses, c'est un concept marrant, sur lequel je vais me pencher, mais je risque d'en avoir pour au moins une semaine ^^...
          juste une question, la cellule en diagonale est considérées comme voisine ?
          • Partager sur Facebook
          • Partager sur Twitter

          Stringman : plateforme en tilemap + météo. Testez le rendu ici. w pour alterner météo.

            12 septembre 2011 à 18:08:57

            Oui je crois.
            • Partager sur Facebook
            • Partager sur Twitter
            Staff désormais retraité.
              12 septembre 2011 à 18:25:02

              Citation : Mr21

              Ahh j'ai testé c'est cool!

              [...] Et pouvoir dessiner pendant que ça joue serait sympa aussi jpense


              Tu peux dessiner si tu mets en pause.
              • Partager sur Facebook
              • Partager sur Twitter
                12 septembre 2011 à 21:13:33

                salut,
                bon, finalement, j'ai fait un truc qui semble marcher, par contre, j'ai un petit souci, tous mes "organismes" meurent ou s'arrêtent d'évoluer.
                Du coup pour la vie, c'est pas terrible...

                main :

                #include <stdlib.h>
                #include <stdio.h>
                #include <SDL.h>
                #include "constantes.h"
                #include "fonctions.h"
                
                int main ( int argc, char** argv )
                {
                    (void)argc;
                    (void)argv;
                
                    /* initialisation SDL video */
                    if ( SDL_Init( SDL_INIT_VIDEO ) < 0 )
                    {/*gestion de l'echec*/
                        printf( "Err / main init SDL: %s\n", SDL_GetError() );
                        exit(EXIT_FAILURE);
                    }
                    else /*init SDL OK*/
                        atexit(SDL_Quit);
                
                    /* creation de la fenêtre*/
                    SDL_Surface* ecran = SDL_SetVideoMode(LARG_TAB*TAILLE_BLOCK, HAUT_TAB*TAILLE_BLOCK, 16,
                                                           SDL_HWSURFACE|SDL_DOUBLEBUF);
                    if ( !ecran )
                    {
                        printf("Err création de la fenêtre 640x480 video: %s\n", SDL_GetError());
                        exit(EXIT_FAILURE);
                    }
                
                    ETAT tab[2][LARG_TAB][HAUT_TAB];
                
                    init_table(tab);
                
                
                    BOOL fin=FALSE,
                        pause=TRUE,
                        index=FALSE;
                    while (!fin)
                    {
                
                        SDL_Event event;
                
                        while (SDL_PollEvent(&event))
                        {
                
                            switch (event.type)
                            {
                
                                case SDL_QUIT:/*croix quitter*/
                                    fin = TRUE;
                                    break;
                
                
                                case SDL_KEYDOWN:/*touches*/
                                    {
                                        if (event.key.keysym.sym == SDLK_SPACE)
                                            pause=TRUE;
                                        break;
                                    }
                                } /* fin de switch*/
                        } /*fin d'acquisition*/
                
                        if (pause)
                        {/*pause et edition*/
                            SDL_Flip(ecran);
                            if (!fill_surface(ecran,tab,index))
                                fin=TRUE;
                
                            pause=FALSE;
                        }
                
                        index=maj_tableau(ecran, tab, index);
                
                        SDL_Delay(100);
                
                        SDL_Flip(ecran);
                
                    } /* fin de boucle principale*/
                
                    return (EXIT_SUCCESS);
                }
                


                constantes.h :
                #ifndef CONSTANTES_H_INCLUDED
                #define CONSTANTES_H_INCLUDED
                
                #define LARG_TAB 100
                #define HAUT_TAB 100
                #define TAILLE_BLOCK 5 /* 5x5 pixels*/
                
                typedef enum{FALSE=0,TRUE=1}BOOL;
                typedef enum{MORT=0,VIE=1}ETAT;
                
                #endif /* CONSTANTES_H_INCLUDED */
                


                fonctions.h :
                #ifndef FONCTIONS_H_INCLUDED
                #define FONCTIONS_H_INCLUDED
                
                void init_table(ETAT tab[2][LARG_TAB][HAUT_TAB]);
                
                BOOL test_vie(ETAT tab[2][LARG_TAB][HAUT_TAB],int x,int y,BOOL index);
                
                BOOL blit_vie(SDL_Surface *ecran,SDL_Rect *position);
                
                BOOL test_mort(ETAT tab[2][LARG_TAB][HAUT_TAB],int x,int y,BOOL index);
                
                BOOL blit_mort(SDL_Surface *ecran,SDL_Rect *position);
                
                BOOL maj_tableau(SDL_Surface* ecran, ETAT tab[2][LARG_TAB][HAUT_TAB], BOOL index);
                
                BOOL fill_surface(SDL_Surface *ecran,ETAT tab[2][LARG_TAB][HAUT_TAB],BOOL index);
                
                #endif /* FONCTIONS_H_INCLUDED */
                


                fonctions.c :
                #include <stdlib.h>
                #include <stdio.h>
                #include <SDL.h>
                #include "constantes.h"
                #include "fonctions.h"
                
                void init_table(ETAT tab[2][LARG_TAB][HAUT_TAB])
                {/*vide le tableau*/
                    unsigned int i,j,k;
                
                    for (k=0;k<2;k++)
                        for (j=0;j<HAUT_TAB;j++)
                            for (i=0;i<LARG_TAB;i++)
                                tab[k][j][i]=MORT;
                }
                
                
                BOOL test_vie(ETAT tab[2][LARG_TAB][HAUT_TAB],int x,int y,BOOL index)
                {/*laisse la vie..ou pas*/
                
                    BOOL retour=FALSE;
                
                    int compte=0,/*nombre de cellules en vie*/
                        i,j;
                
                    for (i=(y-1);i<=(y+1);i++)
                    {
                        for (j=(x-1);j<=(x+1);j++)
                        {
                            if ((j>=0) && (i>=0) && !(i==y && j==x) && (j<LARG_TAB) && (i<HAUT_TAB))
                            {
                                if (tab[index][j][i]==VIE)
                                    compte++;
                            }
                        }
                    }
                
                    if ((compte==2) || (compte==3))
                        retour=TRUE;
                /*
                    printf("test_vie : compte=%d  retour=%d x=%d  y=%d\n",compte,retour,y,y);*/
                
                    return(retour);
                }
                
                
                BOOL blit_vie(SDL_Surface *ecran,SDL_Rect *position)
                {/*blit un pixel vivant*/
                
                    BOOL retour=TRUE;
                
                    if ((SDL_FillRect(ecran,position,SDL_MapRGB(ecran->format,255,255,255)))<0)
                    {/*gestion de l'erreur*/
                        printf("Err / blit_vie : erreur de colorisation en %d x %d :%s",position->x,position->y,SDL_GetError());
                        retour=FALSE;
                    }
                
                    return(retour);
                }
                
                
                BOOL test_mort(ETAT tab[2][LARG_TAB][HAUT_TAB],int x,int y,BOOL index)
                {/*redonne la vie...ou pas*/
                
                    BOOL retour=FALSE;
                
                    int compte=0,/*nombre de cellules en vie*/
                        i,j;
                
                    for (i=(y-1);i<=(y+1);i++)
                    {
                        for (j=(x-1);j<=(x+1);j++)
                        {
                            if ((j>=0) && (i>=0) && !(j==x && i==y) && (j<LARG_TAB) && (i<HAUT_TAB))
                            {
                                if (tab[index][j][i]==VIE)
                                    compte++;
                            }
                        }
                    }
                
                    if (compte==3)
                        retour=TRUE;
                /*
                    printf("test_mort : compte=%d  retour=%d x=%d y=%d\n",compte,retour,x,y);*/
                
                    return(retour);
                }
                
                
                BOOL blit_mort(SDL_Surface *ecran,SDL_Rect *position)
                {/*blit un pixel mort*/
                
                    BOOL retour=TRUE;
                
                    if ((SDL_FillRect(ecran,position,SDL_MapRGB(ecran->format,0,0,0)))<0)
                    {/*gestion de l'erreur*/
                        printf("Err / blit_mort : erreur de colorisation en %d x %d :%s",position->x,position->y,SDL_GetError());
                        retour=FALSE;
                    }
                
                    return(retour);
                }
                
                
                BOOL maj_tableau(SDL_Surface* ecran, ETAT tab[2][LARG_TAB][HAUT_TAB], BOOL index)
                {/*mise à jour de la table suivante et affichage de l'actuelle*/
                
                    int i=0,j=0;
                
                    BOOL nextTabIndex=(index^1),
                    etatActuel=FALSE;
                
                    SDL_Rect blitPos;
                    blitPos.h=TAILLE_BLOCK;
                    blitPos.w=TAILLE_BLOCK;
                
                    for (i=0;i<HAUT_TAB;i++)
                    {
                        for(j=0;j<LARG_TAB;j++)
                        {
                            blitPos.x=j*TAILLE_BLOCK;
                            blitPos.y=i*TAILLE_BLOCK;
                
                            etatActuel=tab[index][j][i];
                
                            if (etatActuel==VIE)
                            {
                                tab[nextTabIndex][j][i]=test_vie(tab,j,i,index);
                
                                if (!blit_vie(ecran,&blitPos))
                                    printf("Err / maj_tableau \n");
                            }
                            else
                            {
                                tab[nextTabIndex][j][i]=test_mort(tab,j,i,index);
                
                                if (!blit_mort(ecran,&blitPos))
                                printf("Err / maj_tableau \n");
                            }
                        }
                    }
                    return(nextTabIndex);
                }
                
                
                BOOL fill_surface(SDL_Surface *ecran,ETAT tab[2][LARG_TAB][HAUT_TAB],BOOL index)
                {/*rempli l'écran manuellement*/
                
                    BOOL fin=FALSE,
                        retour=TRUE,
                        leftBtDown=FALSE,
                        rightBtDown=FALSE;
                    SDL_Event event;
                    SDL_Rect blitPos;
                    int x,y;
                    blitPos.x=blitPos.y=0;
                    blitPos.h=blitPos.w=TAILLE_BLOCK;
                
                    while(!fin)
                    {
                        SDL_WaitEvent(&event);
                
                        switch (event.type)
                        {
                            case SDL_MOUSEBUTTONDOWN :
                
                                x=event.button.x/TAILLE_BLOCK;
                                y=event.button.y/TAILLE_BLOCK;
                                blitPos.x=x*TAILLE_BLOCK;
                                blitPos.y=y*TAILLE_BLOCK;
                
                                switch (event.button.button)
                                {
                
                                    case SDL_BUTTON_LEFT :
                                        leftBtDown=TRUE;
                                        tab[index][x][y]=TRUE;
                                        blit_vie(ecran,&blitPos);
                                    break;
                
                                    case SDL_BUTTON_RIGHT :
                                        rightBtDown=TRUE;
                                        tab[index][x][y]=FALSE;
                                        blit_mort(ecran,&blitPos);
                                    break;
                
                                    default :
                                    break;
                                }
                            break;
                
                            case SDL_MOUSEBUTTONUP :
                
                                switch (event.button.button)
                                {
                                    case SDL_BUTTON_LEFT :
                                        leftBtDown=FALSE;
                                    break;
                
                                    case SDL_BUTTON_RIGHT :
                                        rightBtDown=FALSE;
                                    break;
                
                                    default :
                                    break;
                                }
                            break;
                
                            case SDL_MOUSEMOTION :
                
                                x=event.motion.x/TAILLE_BLOCK;
                                y=event.motion.y/TAILLE_BLOCK;
                                blitPos.x=x*TAILLE_BLOCK;
                                blitPos.y=y*TAILLE_BLOCK;
                
                                if (leftBtDown)
                                {
                                    tab[index][x][y]=TRUE;
                                    blit_vie(ecran,&blitPos);
                                }
                                else if (rightBtDown)
                                {
                                    tab[index][x][y]=FALSE;
                                    blit_mort(ecran,&blitPos);
                                }
                
                            break;
                
                            case SDL_KEYDOWN :
                                switch (event.key.keysym.sym)
                                {
                                    case SDLK_SPACE :
                                        fin=TRUE;
                                    break;
                
                                    case SDLK_DELETE :
                                        init_table(tab);
                
                                        for (y=0;y<HAUT_TAB;y++)
                                            for (x=0;x<LARG_TAB;x++)
                                            {
                                                blitPos.x=x*TAILLE_BLOCK;
                                                blitPos.y=y*TAILLE_BLOCK;
                
                                                blit_mort(ecran,&blitPos);
                                            }
                                        SDL_Flip(ecran);
                                    break;
                
                                    default :
                                    break;
                                }
                            break;
                
                            case SDL_QUIT :
                                fin=TRUE;
                                retour=FALSE;
                
                            default :
                            break;
                        }
                
                        SDL_Flip(ecran);
                    }
                
                    return(retour);
                }
                


                un vrai massacre, personne ne survie...

                PS, soyez indulgeants, il y a ptet un truc en 4 lignes mais bon...

                Edit : code corrigé @Mon ouïe : effectivement la case elle-même était prise en compte ^^ , merci ..

                : une barre de 10 se maintien en mouvement...

                Re-édit, c'est terrible ce truc... : trouvé par pur hasard : 2 fleurs animées il faut de la place autour (suis en 100*100):

                Image utilisateur
                et celui là envoi des "marcheurs" dans tous les sens :
                Image utilisateur

                • Partager sur Facebook
                • Partager sur Twitter

                Stringman : plateforme en tilemap + météo. Testez le rendu ici. w pour alterner météo.

                  12 septembre 2011 à 23:32:45

                  C’est parce qu’il y a une erreur dans ta fonction test_vie :
                  for (i=y-1;i<=y+1;i++)
                          for (j=x-1;j<=x+1;j++)
                          {
                              if (j>=0 && i>=0 && j<LARG_TAB && i<LARG_TAB)
                              {
                                  if (tab[j][i])
                                      compte++;
                              }
                          }
                  


                  Tu comptes la cellule (x, y) comme l’un de ses voisins vivants ; il faut seulement considérer les 8 cellules voisines, pas la cellule elle-même.
                  • Partager sur Facebook
                  • Partager sur Twitter
                    13 septembre 2011 à 18:35:12

                    Citation : GurneyH

                    Il me semble qu'il faut utiliser 2 tableaux.
                    C'est ce que j'ai fait en tout cas. :-°


                    Ah oui, effectivement, je n'y avais pas pensé, ça change tout en fait :p

                    Voici ma version corrigée (version 2 toujours, donc) :
                    #include <stdio.h>
                    #include <stdlib.h>
                    #include <string.h>
                    #include <SDL/SDL.h>
                    
                    #define COLS 640
                    #define ROWS 480
                    #define MODE SDL_HWSURFACE | SDL_DOUBLEBUF
                    
                    #define FPS 25
                    
                    int main(int argc, char ** argv) {
                        SDL_Surface * screen;
                    
                        Uint32 black;
                        Uint32 white;
                    
                        int grid[1 + COLS + 1][1 + ROWS + 1];
                    
                        int onclick = 0;
                        int onpause = 0;
                        int onclear = 0;
                        int running = 1; 
                    
                    /* init ------------------------------------------------------------- */
                        if (SDL_Init(SDL_INIT_VIDEO) == -1) {
                            fprintf(stderr, "fatal: %s\n", SDL_GetError());
                            exit(EXIT_FAILURE);
                        }
                        
                        if ((screen = SDL_SetVideoMode(COLS, ROWS, 32, MODE)) == NULL) {
                            fprintf(stderr, "fatal: %s\n", SDL_GetError());
                            exit(EXIT_FAILURE);
                        }
                    
                        black = SDL_MapRGB(screen->format, 0xFF, 0xFF, 0xFF);
                        white = SDL_MapRGB(screen->format, 0x00, 0x00, 0x00);
                    
                        SDL_WM_SetCaption("Game of Life", NULL);
                    
                        memset(grid, 0, sizeof grid);
                    
                        for (;;) {
                            int x, y;
                            SDL_Event event;
                    
                    /* handle events ---------------------------------------------------- */
                            while (SDL_PollEvent(&event)) {
                                switch (event.type) {
                                    case SDL_MOUSEBUTTONDOWN:
                                        onclick = 1;
                                        break;
                    
                                    case SDL_MOUSEBUTTONUP:
                                        onclick = 0;
                                        break;
                    
                                    case SDL_MOUSEMOTION:
                                        x = 1 + event.motion.x;
                                        y = 1 + event.motion.y;
                                        break;
                    
                                    case SDL_KEYDOWN:
                                        switch (event.key.keysym.sym) {
                                            case SDLK_p:
                                                onpause = 1;
                                                break;
                    
                                            case SDLK_r:
                                                onclear = 1;
                                                break;
                    
                                            default:
                                                ;
                                        }
                                        break;
                    
                                    case SDL_QUIT:
                                        goto quit;
                    
                                    default:
                                        ;
                                }
                    
                    /* process events --------------------------------------------------- */
                                if (onclick) {
                                    grid[x][y] = 1;
                                }
                    
                                if (onpause) {
                                    running ^= 1;
                    
                                    if (running) {
                                        SDL_WM_SetCaption("Game of Life", NULL);
                                    }
                                    else {
                                        SDL_WM_SetCaption("Game of Life (paused)", NULL);
                                    }
                    
                                    onpause = 0;
                                }
                    
                                if (onclear) {
                                    memset(grid, 0, sizeof grid);
                    
                                    onclear = 0;
                                }
                            }
                    
                    /* update ----------------------------------------------------------- */
                            if (running) {
                                int temp[1 + COLS + 1][1 + ROWS + 1];
                    
                                memcpy(temp, grid, sizeof grid);
                    
                                for (x = 1; x < 1 + COLS; x++) {
                                    for (y = 1; y < 1 + ROWS; y++) {
                                        int n = 0;
                    
                                        n += temp[x][y - 1];
                                        n += temp[x][y + 1];
                                        n += temp[x - 1][y];
                                        n += temp[x + 1][y];
                                        n += temp[x - 1][y - 1];
                                        n += temp[x - 1][y + 1];
                                        n += temp[x + 1][y - 1];
                                        n += temp[x + 1][y + 1];
                    
                                        if (temp[x][y]) {
                                            grid[x][y] = n == 2 || n == 3;
                                        }
                                        else {
                                            grid[x][y] = n == 3;
                                        }
                                    }
                                }
                            }
                    
                    /* render ----------------------------------------------------------- */
                            for (y = 1; y < 1 + ROWS; y++) {
                                for (x = 1; x < 1 + COLS; x++) {
                                    Uint32 * pixel = (Uint32 *) screen->pixels;
                    
                                    pixel += (y - 1) * screen->pitch / 4 + (x - 1);
                    
                                    if (grid[x][y]) {
                                        *pixel = black;
                                    }
                                    else {
                                        *pixel = white;
                                    }
                                }
                            }
                    
                            SDL_Flip(screen);
                            SDL_Delay(1000 / FPS);
                        }
                    
                    /* quit ------------------------------------------------------------- */
                    quit:
                        SDL_Quit();
                            
                        (void) argc;
                        (void) argv;
                    
                        return 0;
                    }
                    

                    Toujours les mêmes touches, on peut répandre des cellules en cliquant avec la souris à tout moment, P pour mettre en pause, R pour effacer l'écran.

                    EDIT: petite optimisation...
                    • Partager sur Facebook
                    • Partager sur Twitter
                      13 septembre 2011 à 18:48:43

                      Ahhh c'est pas mal ça!
                      Par contre il y a le bug habituel qui fait que si je clique et que je me déplace assez vite bah ça ne me met qu'un point tout deux kilomètres...

                      Une cellule/un pixel jtrouve ça parfait!
                      Mais on devrait pouvoir zoomer pour voir vraiment ce qu'on fait.
                      Typiquement, là, j'aurais pas pu essayer de faire un U comme m'a dit yoch...
                      Mais bon jtrouve ça déjà excellent et ça me fait mal de dire d'un projet sans fonction :S

                      Par contre P pour faire Pause ça craint un peu, faut le chercher le P alors que la barre espace est beaucoup mieux pour ça j'pense, mais bon c'est un détail.

                      OMG comment c'est classe de faire une ligne droite!!!
                      • Partager sur Facebook
                      • Partager sur Twitter
                        13 septembre 2011 à 20:12:53

                        Citation : Mr21

                        Par contre il y a le bug habituel qui fait que si je clique et que je me déplace assez vite bah ça ne me met qu'un point tout deux kilomètres...


                        C'est dû au fait que l'event "déplacement souris" n'est pas forcément envoyé à chaque pixel de déplacement, lors d'un déplacement rapide. S'il faut gérer ça, suffit de tracer des traits à chaque fois (je serais d'ailleurs curieux de voir si la SDL peut rater un tracé de courbe ultra rapide dans ces conditions).
                        • Partager sur Facebook
                        • Partager sur Twitter
                          13 septembre 2011 à 20:17:40

                          Oui voilà exactement, il faut le drawline (premier exercice graphique qu'on fait à mon école ^^)

                          Dans notre cas, il faut garder en mémoire la position du dernier point et tracer la droite entre les deux.
                          Mais il est vrai que c'est un peu plus dur, mais ça rendra clairement mieux!

                          Et la SDL ne peux pas rater un trait car tu auras toujours les coordonnées du point d'avant (il faut un cas particulier pour le premier clique).
                          • Partager sur Facebook
                          • Partager sur Twitter
                            23 septembre 2011 à 15:57:08

                            Salut,

                            Je viens de finir le programme, je sais que je viens en retarde, mais c'est du au manque de temps, j'ai un/des projets en cours en plus du lycée.

                            Le code :

                            #include <stdio.h>
                            #include <time.h>
                            #include <SDL.h>
                            
                            #define TAILLE 10
                            #define NOMBRE_BLOCS 50
                            #define FILE_NAME_S "save.gl"
                            #define FILE_NAME_L "load.gl"
                            
                            int init();
                            SDL_Surface* creeFenetre(int largeur, int hauteur, int nbrCouleur, Uint32 arguments, char nomF[]);
                            SDL_Surface* creeBloc();
                            void afficheMap(char map[][NOMBRE_BLOCS], SDL_Surface* ecran, SDL_Surface* bloc);
                            void copieMap(char map[][NOMBRE_BLOCS], char map1[][NOMBRE_BLOCS]);
                            void generateMap(char map[][NOMBRE_BLOCS], int choix);
                            void teste(char map[][NOMBRE_BLOCS], char map1[][NOMBRE_BLOCS]);
                            void Save(char map[][NOMBRE_BLOCS]);
                            void Load(char map[][NOMBRE_BLOCS]);
                            
                            int main ( int argc, char** argv )
                            {
                                SDL_Surface *ecran = NULL, *bloc = NULL;
                                SDL_Event event;
                                char map[NOMBRE_BLOCS][NOMBRE_BLOCS];
                                char map1[NOMBRE_BLOCS][NOMBRE_BLOCS];
                                int continuer = 1, delay = 100, delay1 = 0, etat = 0;
                            
                                srand(time(NULL));
                                init();
                                ecran = creeFenetre(TAILLE * NOMBRE_BLOCS, TAILLE * NOMBRE_BLOCS, 32, SDL_HWSURFACE, "Jeu De La Vie");
                                bloc = creeBloc();
                            
                                generateMap(map, -1);
                                copieMap(map, map1);
                                SDL_EnableKeyRepeat(0, 0);
                                while(continuer)
                                {
                                    while(SDL_PollEvent(&event))
                                    {
                                        switch(event.type)
                                        {
                                            case SDL_QUIT :
                                            continuer = 0;
                                            break;
                                            case SDL_MOUSEBUTTONUP :
                                            if(!etat && event.button.button == SDL_BUTTON_LEFT)
                                            {
                                                map[event.button.x / TAILLE][event.button.y / TAILLE] ^= 1;
                                                map1[event.button.x / TAILLE][event.button.y / TAILLE] ^= 1;
                                            }
                                            else if(etat && (event.button.button == SDL_BUTTON_WHEELUP || event.button.button == SDL_BUTTON_WHEELDOWN))
                                            {
                                                delay += event.button.button == SDL_BUTTON_WHEELUP ? (delay > 0 ? -1 : 0) : +1;
                                            }
                                            break;
                                            case SDL_KEYDOWN :
                                            switch(event.key.keysym.sym)
                                            {
                                                case SDLK_p :
                                                etat ^= 1;
                                                break;
                                                case SDLK_SPACE :
                                                SDL_SaveBMP(ecran, "screen.bmp");
                                                break;
                                                case SDLK_KP1 :
                                                if(!etat)
                                                {
                                                    generateMap(map, 1);
                                                    copieMap(map, map1);
                                                }
                                                break;
                                                case SDLK_KP0 :
                                                if(!etat)
                                                {
                                                    generateMap(map, 0);
                                                    copieMap(map, map1);
                                                }
                                                break;
                                                case SDLK_KP2 :
                                                if(!etat)
                                                {
                                                    generateMap(map, -1);
                                                    copieMap(map, map1);
                                                }
                                                break;
                                                case SDLK_s :
                                                Save(map);
                                                break;
                                                case SDLK_l :
                                                if(!etat)
                                                {
                                                    Load(map);
                                                    copieMap(map, map1);
                                                }
                                                break;
                                                default :
                                                ;
                                                break;
                                            }
                                            break;
                                            default :
                                            ;
                                            break;
                                        }
                                    }
                                if(etat)
                                teste(map, map1);
                                afficheMap(map, ecran, bloc);
                                SDL_Delay(etat ? delay : delay1);
                                }
                            
                                SDL_FreeSurface(bloc);
                                return EXIT_SUCCESS;
                            }
                            
                            int init()
                            {
                            
                                if(SDL_Init(SDL_INIT_VIDEO) < 0)
                                {
                                    fprintf(stderr, "Erreur d'initialisation de la SDL: %s\n", SDL_GetError());
                                    exit(EXIT_FAILURE);
                                }
                                atexit(SDL_Quit);
                            
                                return 0;
                            }
                            
                            SDL_Surface* creeFenetre(int largeur, int hauteur, int nbrCouleur, Uint32 arguments, char nomF[])
                            {
                                SDL_Surface* ecran = NULL;
                            
                                ecran = SDL_SetVideoMode(largeur, hauteur, nbrCouleur, arguments);
                                SDL_WM_SetCaption(nomF, NULL);
                            
                                if(!ecran)
                                {
                                    fprintf(stderr, "Erreur de creation de la fenetre : %s\n", SDL_GetError());
                                    exit(EXIT_FAILURE);
                                }
                            
                                return ecran;
                            }
                            
                            SDL_Surface* creeBloc()
                            {
                                SDL_Surface* bloc = NULL;
                                SDL_Rect parti;
                                int i;
                            
                                parti.h = parti.w = TAILLE;
                                parti.y = 0;
                            
                                bloc = SDL_CreateRGBSurface(SDL_HWSURFACE, TAILLE * 2, TAILLE, 32, 0, 0, 0,0);
                                if(!bloc)
                                {
                                    fprintf(stderr, "Erreur de creation de l'allocation d'une surface : %s\n", SDL_GetError());
                                    exit(EXIT_FAILURE);
                                }
                                for(i = 0; i < 2; i++)
                                {
                                    parti.x = i * TAILLE;
                                    SDL_FillRect(bloc, &parti, ~(0xffffff * i));
                                }
                            
                                return bloc;
                            }
                            
                            void afficheMap(char map[][NOMBRE_BLOCS], SDL_Surface* ecran, SDL_Surface* bloc)
                            {
                                SDL_Rect parti, pos;
                                int i, j;
                            
                                parti.y = 0;
                                parti.w = parti.h = TAILLE;
                            
                                for(i = 0; i < NOMBRE_BLOCS; i++)
                                {
                                    for(j = 0; j < NOMBRE_BLOCS; j++)
                                    {
                                        parti.x = map[i][j] * TAILLE;
                                        pos.x = i * TAILLE;
                                        pos.y = j * TAILLE;
                                        SDL_BlitSurface(bloc, &parti, ecran, &pos);
                                    }
                                }
                                SDL_Flip(ecran);
                            }
                            
                            void copieMap(char map[][NOMBRE_BLOCS], char map1[][NOMBRE_BLOCS])
                            {
                                int i, j;
                            
                                for(i = 0; i < NOMBRE_BLOCS; i++)
                                    for(j = 0; j < NOMBRE_BLOCS; j++)
                                        map1[i][j] = map[i][j];
                            
                            }
                            
                            void generateMap(char map[][NOMBRE_BLOCS], int choix)
                            {
                                int i, j;
                            
                                for(i = 0; i < NOMBRE_BLOCS; i++)
                                    for(j = 0; j < NOMBRE_BLOCS; j++)
                                        map[i][j] = choix >= 0 ? choix : rand() % 2;
                            }
                            
                            void teste(char map[][NOMBRE_BLOCS], char map1[][NOMBRE_BLOCS])
                            {
                                int i, j, k, l, nbr_voisine_vivante;
                            
                                for(i = 0; i < NOMBRE_BLOCS; i++)
                                {
                                    for(j = 0; j < NOMBRE_BLOCS; j++)
                                    {
                                        nbr_voisine_vivante = 0;
                                        for(k = -1; k < 2; k++)
                                            for(l = -1; l < 2; l++)
                                                if((k != 0 || l != 0) && (i != 0 || k != (-1)) && (i != NOMBRE_BLOCS-1 || k != 1) && (j != 0 || l != (-1)) && (j != NOMBRE_BLOCS-1 || l!= 1))
                                                    nbr_voisine_vivante += map1[i+k][j+l];
                            
                                        map[i][j] = (map1[i][j] && (nbr_voisine_vivante == 2 || nbr_voisine_vivante == 3)) || !map1[i][j] && nbr_voisine_vivante == 3 ? 1 : 0;
                                    }
                                }
                                copieMap(map, map1);
                            }
                            
                            void Save(char map[][NOMBRE_BLOCS])
                            {
                                FILE * save;
                                int i, j;
                            
                                save = fopen(FILE_NAME_S, "w");
                                if(save)
                                {
                                    for(i = 0; i < NOMBRE_BLOCS; i++)
                                    {
                                        for(j = 0; j < NOMBRE_BLOCS; j++)
                                        fputc(map[i][j], save);
                                        if(i < NOMBRE_BLOCS-1)
                                        fputc('\n', save);
                                    }
                            
                                    fclose(save);
                                }
                            }
                            
                            void Load(char map[][NOMBRE_BLOCS])
                            {
                                FILE * load;
                                int i, j;
                            
                                load = fopen(FILE_NAME_L, "r");
                                if(load)
                                {
                                    for(i = 0; i < NOMBRE_BLOCS; i++)
                                    {
                                        for(j = 0; j < NOMBRE_BLOCS; j++)
                                        map[i][j] = fgetc(load);
                                        fgetc(load);
                                    }
                            
                                    fclose(load);
                                }
                            }
                            



                            Utilisation :
                            P : mettre en Pause/Relancer
                            ESPACE : Prendre un screen
                            0 : Effacer l’écran (Uniquement en mode Pause)
                            1 : Remplir Tout l’écran avec des cellules vivantes (Uniquement en mode Pause)
                            2 : Remplir l'écran aléatoirement (Uniquement en mode Pause)
                            La mollette de la souris : accélérée/ralentir (Uniquement en Mode Play)
                            s : Sauvegarder dans un fichier .gl (par default save.gl)
                            l : Lire un fichier .gl (par default load.gl)

                            Pour la fonction Load : je dois la modifier pour qu'elle soit utilisable pour une grille de n'importe quelle taille.
                            La grille est rempli aléatoirement au lancement du programme.
                            • Partager sur Facebook
                            • Partager sur Twitter
                              6 novembre 2016 à 18:30:21

                              Désolé pour le déterrage, j'ai commencé le C il y a 6 jours.

                              voici mon code, il démarre en pause, merci pour vos conseils.

                              p = pause/reprise

                              esc = quitter

                              mouse+clic-gauche = ajouter cellules

                              #include <stdlib.h>
                              #include <stdio.h>
                              #include <SDL/SDL.h>
                              #include <time.h> 
                              
                              
                              
                              typedef struct cellule cellule;
                              typedef struct petri petri;
                              
                              
                              SDL_Surface* screen;
                              SDL_Event event;
                              char pause;
                              int numcell;
                              int nait;
                              int meurt;
                              
                              struct cellule
                              	{
                              	int x;
                              	int y;
                              	char status;
                              	char compteur;
                              	cellule* next;
                              	};
                              	
                              
                              struct petri
                              	{
                              	int width;
                              	int height;
                              	cellule* listCell;
                              	cellule** table;
                              	};
                              
                              
                              SDL_Surface* setMode(int w, int h)
                              	{
                              	if(SDL_Init(SDL_INIT_VIDEO)==-1){exit(EXIT_FAILURE);}
                              	return SDL_SetVideoMode(w, h , 32, SDL_HWSURFACE);
                              	}
                              
                              
                              void putpixel(SDL_Surface* screen, int x, int y)
                              	{
                              	Uint8 *p = (Uint8 *)screen->pixels + y * screen->pitch + x * 4;
                              	*(Uint32 *)p = SDL_MapRGB(screen->format, 200, 200, 200);
                              	}
                              	
                              petri* setPetri(int width, int height)
                              	{
                              	screen	       = setMode(width,height);
                              	width = screen->w;
                              	height = screen->h;
                              	petri* culture     = malloc(sizeof(petri));
                              	culture->listCell  = NULL;
                              	culture->table     = malloc((long unsigned)width*sizeof(cellule*));
                              	int xx, yy;
                              	for(xx=0;xx<width;xx++)
                              		{
                              		culture->table[xx] = malloc((long unsigned)height*sizeof(cellule));
                              		for(yy=0;yy<height;yy++)
                              			{
                              			culture->table[xx][yy].x	= xx;
                              			culture->table[xx][yy].y	= yy;
                              			culture->table[xx][yy].status	= 0;
                              			culture->table[xx][yy].compteur	= 0;
                              			culture->table[xx][yy].next	= NULL;
                              			}
                              		}
                              	culture->width  = width;
                              	culture->height = height;
                              	return culture;
                              	}
                              
                              void setCellule(petri *culture, int x, int y)
                              	{
                              	culture->table[x][y].compteur = 0;
                              	if(culture->table[x][y].status==0)
                              		{
                              		culture->table[x][y].status = 1;
                              		culture->table[x][y].next = culture->listCell;
                              		culture->listCell = &culture->table[x][y];
                              		}
                              	}
                              
                              void updateCell(petri *culture, int x, int y)
                              	{
                              	if(x>=0 && x<culture->width && y>=0 && y<culture->height)
                              		{
                              		if(!culture->table[x][y].status && !culture->table[x][y].compteur)
                              			{
                              			culture->table[x][y].next = culture->listCell;
                              			culture->listCell = &culture->table[x][y];
                              			}
                              		culture->table[x][y].compteur++;
                              		}
                              	}
                              
                              
                              void update(petri *culture)
                              	{
                              	cellule* alive = culture->listCell;
                              	cellule* tmp   = culture->listCell;
                              	numcell = 0;
                              	nait = 0;
                              	meurt = 0;
                              	while(tmp!=NULL)
                              		{
                              		updateCell(culture,tmp->x,tmp->y+1);
                              		updateCell(culture,tmp->x,tmp->y-1);
                              		updateCell(culture,tmp->x+1,tmp->y);
                              		updateCell(culture,tmp->x-1,tmp->y);
                              		updateCell(culture,tmp->x+1,tmp->y+1);
                              		updateCell(culture,tmp->x+1,tmp->y-1);
                              		updateCell(culture,tmp->x-1,tmp->y+1);
                              		updateCell(culture,tmp->x-1,tmp->y-1);
                              		tmp = tmp->next;
                              		}
                              	tmp = culture->listCell;
                              	cellule** tmp0 = &culture->listCell;
                              	while(tmp!=alive)
                              		{
                              		if(tmp->compteur==3)
                              			{
                              			tmp->status = 1;
                              			tmp->compteur = 0;
                              			*tmp0 = tmp;
                              			tmp0 = &tmp->next;
                              			numcell++;
                              			putpixel(screen,tmp->x, tmp->y);
                              			}
                              		else
                              			{
                              			culture->table[tmp->x][tmp->y].status   = 0;
                              			culture->table[tmp->x][tmp->y].compteur = 0;
                              			}
                              		nait = numcell;
                              		tmp = tmp->next;
                              		}
                              	while(tmp!=NULL)
                              		{
                              		if(tmp->compteur==2||tmp->compteur==3)
                              			{
                              			tmp->compteur = 0;
                              			*tmp0 = tmp;
                              			tmp0 = &tmp->next;
                              			numcell++;
                              			putpixel(screen,tmp->x, tmp->y);
                              			}
                              		else
                              			{
                              			culture->table[tmp->x][tmp->y].status   = 0;
                              			culture->table[tmp->x][tmp->y].compteur = 0;
                              			meurt++;
                              			}
                              		tmp = tmp->next;
                              		}
                              	*tmp0 = NULL;
                              	SDL_Flip(screen);
                              	SDL_FillRect(screen, NULL, 0);
                              	}
                               
                              void generation(petri *culture)
                              	{
                              	pause = 1;
                              	int gen = 0;
                              	while(1)
                              		{
                              		while(SDL_PollEvent(&event))
                              			{
                              			if(event.type==SDL_KEYDOWN)
                              				{
                              				switch(event.key.keysym.sym)
                              					{
                              					case SDLK_p:
                              						pause ^= 1;
                              						break;
                              					case SDLK_ESCAPE:
                              						return;
                              						break;
                              					default:
                              						break;
                              					}
                              				}
                              			else if(event.type==SDL_MOUSEMOTION && event.motion.state==SDL_BUTTON_LEFT)
                              				{
                              				setCellule(culture,event.motion.x,event.motion.y);
                              				putpixel(screen,event.motion.x, event.motion.y);
                              				SDL_UpdateRect(screen,event.motion.x, event.motion.y,1,1);
                              				}
                              			else if(event.type==SDL_MOUSEBUTTONDOWN && event.button.button==SDL_BUTTON_LEFT)
                              				{
                              				setCellule(culture,event.button.x,event.button.y);
                              				putpixel(screen,event.button.x, event.button.y);
                              				SDL_UpdateRect(screen,event.button.x, event.button.y,1,1);
                              				}
                              			}
                              		if(pause==0)
                              			{
                              			printf("gen %d : total %d : naiss %d : deces %d\n",gen,numcell,nait,meurt);
                              			update(culture);
                              			gen++;
                              			}
                              		}
                              	}
                              	
                              void terminus(petri *culture)
                              	{
                              	int i;
                              	for(i=0;i<culture->width;i++)
                              		{
                              		free(culture->table[i]);
                              		}
                              	free(culture->table);
                              	free(culture);
                              	SDL_Quit();
                              	}
                              
                              
                              int main()
                              	{
                              	srand ((unsigned int)time (NULL));
                              	printf("%p",&terminus);
                              	petri* culture = setPetri(600,400);
                              	//~ int w=culture->width, h=culture->height;
                              	//~ int i;
                              	//~ for(i=0;i<w*h;i++)
                              		//~ {
                              		//~ int x = rand()%w;
                              		//~ int y = +rand()%h;
                              		//~ setCellule(culture,x,y);
                              		//~ }
                              	generation(culture);
                              	terminus(culture);
                              	return 0;
                              	}
                              



                              -
                              Edité par josmiley 23 novembre 2016 à 8:07:17

                              • Partager sur Facebook
                              • Partager sur Twitter

                              [FAIT][Défis] #2 : Le jeu de la vie !

                              × Après avoir cliqué sur "Répondre" vous serez invité à vous connecter pour que votre message soit publié.
                              × Attention, ce sujet est très ancien. Le déterrer n'est pas forcément approprié. Nous te conseillons de créer un nouveau sujet pour poser ta question.
                              • Editeur
                              • Markdown