123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381 |
- /*
- * File: handler.c
- * Author: Arthur Brandao
- *
- * Created on 23 novembre 2018
- */
- #include <stdio.h>
- #include <stdlib.h>
- #include <unistd.h>
- #include "error.h"
- #include "bomberstudent_server.h"
- #include "client.h"
- #include "player.h"
- #include "handler.h"
- /* --- Extern --- */
- extern Game game[MAXGAME];
- extern int nbGame;
- /* --- Fonctions privées --- */
- /**
- * Cherche dans quel partie est un client
- * @param int L'id du client
- * @return int L'index de la partie
- */
- int search_client_game(int cliId) {
- int index = ERR;
- for (int i = 0; i < MAXGAME; i++) {
- //Regarde si la game est active et avec des joueurs
- if (game[i].active && game[i].nbPlayer > 0) {
- //Parcours les joueurs
- for (int j = 0; j < MAXPLAYER; j++) {
- //Si le joueur est actif
- if (game[i].player[j]->ini) {
- //Si l'id est le bon
- if (game[i].player[j]->id == cliId) {
- index = i;
- break;
- }
- }
- }
- }
- //Si on a un resultat
- if (index != ERR) {
- break;
- }
- }
- //Retour
- return index;
- }
- /**
- * Cherche une partie par son nom
- * @param char* Le nom de la partie
- * @return int L'index dans le tableau
- */
- int search_game(char* name) {
- int index = ERR;
- for (int i = 0; i < MAXGAME; i++) {
- //Regarde si la game est active et le nom
- if (game[i].active && strncmp(game[i].name, name, strlen(game[i].name)) == 0) {
- index = i;
- break;
- }
- }
- return index;
- }
- /* --- Fonctions publiques --- */
- void ini_handler() {
- //Get
- add_handler("GET", "client/end", handler_client_end);
- add_handler("GET", "game/list", handler_game_list);
- //Post
- add_handler("POST", "game/create", handler_game_create);
- add_handler("POST", "game/join", handler_game_join);
- add_handler("POST", "player/move", handler_player_move);
- }
- int handler_client_end(int cliId, JsonParser* json) {
- boolean find = false;
- JsonEncoder* notif;
- printf("Deconnexion du client %d\n", cliId);
- //Cherche le client dans les parties
- for (int i = 0; i < MAXGAME; i++) {
- if (game[i].active) {
- for (int j = 0; j < MAXPLAYER; j++) {
- if (game[i].player[j]->ini && game[i].player[j]->id == cliId) {
- find = true;
- remove_player(&game[i], j);
- //Avertit les autres joueurs
- notif = malloc(sizeof (JsonEncoder));
- ini_encoder(notif);
- add_integer(notif, "player", cliId);
- notify_player(&game[i], "POST", "game/quit", notif, cliId);
- clean_json_encoder(notif);
- free(notif);
- break;
- }
- }
- if (find) {
- break;
- }
- }
- }
- remove_client(cliId);
- return SUCCESS;
- }
- int handler_game_list(int cliId, JsonParser* json) {
- JsonEncoder reponse;
- JsonArray game;
- JsonArray map;
- int nb;
- //Recup la liste des parties et des cartes
- ini_array_encoder(&game);
- ini_array_encoder(&map);
- nb = list_game(&game);
- list_map(&map);
- //Creation reponse
- ini_encoder(&reponse);
- add_string(&reponse, "action", "game/list");
- add_string(&reponse, "status", "200");
- add_string(&reponse, "message", "ok");
- if (nb == 0) {
- add_integer(&reponse, "numberGameList", 0);
- } else {
- add_integer(&reponse, "numberGameList", nb);
- add_array(&reponse, "games", &game);
- }
- add_array(&reponse, "maps", &map);
- //Envoi reponse au client
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- return FAIL;
- }
- //Nettoyage
- clean_json_encoder(&reponse);
- clean_json_array(&map);
- clean_json_array(&game);
- return SUCCESS;
- }
- int handler_game_create(int cliId, JsonParser* json) {
- char* map, * name, * msg;
- int index, joueur;
- JsonEncoder reponse;
- //Verification arguments
- if (get_pos(json, "name") == JSON_ERROR) {
- send_err_client(cliId, EREQUEST);
- adderror("Le json du client est incorrect");
- return FAIL;
- }
- if (get_pos(json, "map") == JSON_ERROR) {
- send_err_client(cliId, EREQUEST);
- adderror("Le json du client est incorrect");
- return FAIL;
- }
- //Recup valeur
- map = get_string(json, "map");
- name = get_string(json, "name");
- //Initialisation reponse JSON
- ini_encoder(&reponse);
- add_string(&reponse, "action", "game/create");
- //Verif nom non existant
- if (search_game(name) != ERR) {
- add_string(&reponse, "status", "501");
- add_string(&reponse, "message", "Cannot create game");
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- }
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Creation
- index = create_game(name, map);
- if (index == ERR) {
- add_string(&reponse, "status", "501");
- add_string(&reponse, "message", "Cannot create game");
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- }
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Ajout du joueur dans la partie
- joueur = add_player(&game[index], cliId);
- if (joueur == ERR) {
- stop_game(&game[index]);
- add_string(&reponse, "status", "501");
- add_string(&reponse, "message", "Cannot create game");
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- }
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Recup info
- describe_game(&game[index], joueur, &reponse);
- //Ajout infos
- msg = new_string(25 + strlen(map));
- sprintf(msg, "Game created with %s", map);
- add_string(&reponse, "status", "201");
- add_string(&reponse, "message", msg);
- add_string(&reponse, "startPos", "0,0");
- free(msg);
- //Envoi
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Nettoyage
- clean_json_encoder(&reponse);
- free(map);
- free(name);
- return SUCCESS;
- }
- int handler_game_join(int cliId, JsonParser* json) {
- char* name;
- int index, joueur;
- JsonEncoder reponse;
- //Verification arguments
- if (get_pos(json, "name") == JSON_ERROR) {
- send_err_client(cliId, EREQUEST);
- adderror("Le json du client est incorrect");
- return FAIL;
- }
- //Recup valeur
- name = get_string(json, "name");
- //Initialisation json reponse
- ini_encoder(&reponse);
- add_string(&reponse, "action", "game/join");
- //Verif game existe
- index = search_game(name);
- if (index == ERR) {
- add_string(&reponse, "status", "501");
- add_string(&reponse, "message", "Cannot join the game");
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- }
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Ajout du joueur dans la partie
- joueur = add_player(&game[index], cliId);
- if (joueur == ERR) {
- add_string(&reponse, "status", "501");
- add_string(&reponse, "message", "Cannot join the game");
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- }
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Recup info
- describe_game(&game[index], joueur, &reponse);
- //Ajout infos
- add_string(&reponse, "status", "201");
- add_string(&reponse, "startPos", "0,0");
- //Envoi
- if (!send_client(cliId, &reponse)) {
- adderror("Impossible de répondre au client");
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Nettoyage
- clean_json_encoder(&reponse);
- free(name);
- //Avertit les autres joueurs
- add_integer(&reponse, "id", cliId);
- add_string(&reponse, "pos", "0,0");
- notify_player(&game[index], "POST", "game/newplayer", &reponse, cliId);
- //Nettoyage
- clean_json_encoder(&reponse);
- return SUCCESS;
- }
- int handler_player_move(int cliId, JsonParser* json) {
- printf("Player Move\n");
- char* move;
- int index, x = 0, y = 0;
- Player* p = NULL;
- boolean mine = false;
- JsonEncoder reponse;
- //Verification arguments
- if (get_pos(json, "move") == JSON_ERROR) {
- return FAIL;
- }
- //Recup valeur
- move = get_string(json, "move");
- //Verif game existe
- index = search_client_game(cliId);
- if (index == ERR) {
- free(move);
- clean_json_encoder(&reponse);
- return FAIL;
- }
- //Recup le joueur
- for(int i = 0; i < MAXPLAYER; i++){
- if(game[index].player[i]->ini && game[index].player[i]->id == cliId){
- p = game[index].player[i];
- break;
- }
- }
- if(p == NULL){
- free(move);
- return FAIL;
- }
- //Regarde si le joueur peut bouger
- if (strncmp(move, "up", 2) == 0) {
- if(p->y > 0 && !player_collision(&game[index], p->x, p->y - 1) && ( game[index].map[p->x][p->y - 1] == '_' /*Vide*/ || game[index].map[p->x][p->y - 1] == '2' /*Mine*/ )){
- //Bouge le joueur sur la carte
- p->y--;
- //Si marche sur une mine
- if(game[index].map[p->x][p->y] == '2'){
- game[index].map[p->x][p->y] = '_';
- mine = true;
- x = p->x;
- y = p->y;
- }
- }
- } else if (strncmp(move, "down", 4) == 0) {
- if(p->y < game[index].height && !player_collision(&game[index], p->x, p->y + 1) && ( game[index].map[p->x][p->y + 1] == '_' /*Vide*/ || game[index].map[p->x][p->y + 1] == '2' /*Mine*/ )){
- //Bouge le joueur sur la carte
- p->y++;
- //Si marche sur une mine
- if(game[index].map[p->x][p->y] == '2'){
- game[index].map[p->x][p->y] = '_';
- mine = true;
- x = p->x;
- y = p->y;
- }
- }
- } else if (strncmp(move, "left", 4) == 4) {
- if(p->x > 0 && !player_collision(&game[index], p->x - 1, p->y) && ( game[index].map[p->x - 1][p->y] == '_' /*Vide*/ || game[index].map[p->x - 1][p->y] == '2' /*Mine*/ )){
- //Bouge le joueur sur la carte
- p->x--;
- //Si marche sur une mine
- if(game[index].map[p->x][p->y] == '2'){
- game[index].map[p->x][p->y] = '_';
- mine = true;
- x = p->x;
- y = p->y;
- }
- }
- } else if(strncmp(move, "right", 4) == 0){
- if(p->x < game[index].width && !player_collision(&game[index], p->x + 1, p->y) && ( game[index].map[p->x + 1][p->y] == '_' /*Vide*/ || game[index].map[p->x + 1][p->y] == '2' /*Mine*/ )){
- //Bouge le joueur sur la carte
- p->x++;
- //Si marche sur une mine
- if(game[index].map[p->x][p->y] == '2'){
- game[index].map[p->x][p->y] = '_';
- mine = true;
- x = p->x;
- y = p->y;
- }
- }
- } else {
- free(move);
- send_err_client(cliId, EREQUEST);
- adderror("Le json du client est incorrect");
- return FAIL;
- }
- //Notifie les joueurs
- ini_encoder(&reponse);
- add_integer(&reponse, "player", cliId);
- add_string(&reponse, "move", move);
- notify_player(&game[index], "POST", "player/position/update", &reponse, -1);
- //Si marche sur une mine
- if(mine){
- printf("Mine %d %d", x, y);
- }
- //Nettoyage
- clean_json_encoder(&reponse);
- free(move);
- return SUCCESS;
- }
|