Guest User

Untitled

a guest
Jun 20th, 2018
63
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 11.76 KB | None | 0 0
  1. #ifdef MAC
  2. #include <GLUT/glut.h>
  3. #else
  4. #include <GL/gl.h>
  5. #include <GL/glut.h>
  6. #endif
  7.  
  8. /**Faz a inclusao de todas as bibliotecas necessarias a execussao do programa.*/
  9. #include <stdio.h>
  10. #include <stdlib.h>
  11. #include <time.h>
  12. #include <string.h>
  13. #include <ctype.h>
  14.  
  15.  
  16. /**Carrega o ficheiro def.h, tambem necessario para a execussao do programa.*/
  17. #include "def.h"
  18.  
  19.  
  20.  
  21. char *fmapa;
  22. char *fregras;
  23. char *regra;
  24. char *strdelc (char *s, char ch);
  25. char strfstc (char *s);
  26. int estado_valido(char est);
  27. int regra_valida(char *regra);
  28. void display(void);
  29. void init(void);
  30. void ler_mapa(FILE *file_map);
  31. void ler_regra(FILE *file_rules);
  32.  
  33. char *fmapa, *fregras;
  34.  
  35. int getx, gety; /**Vai permitir ler os valores X e Y da matriz do mapa, para que sejam utilizados por todo o programa*/
  36.  
  37. char *tmp_board; /**Board temporario para posteriormente ser subsituido pelo outro board*/
  38.  
  39. char linha[100]; /**Array para armazenar uma linha do ficheiro de regras*/
  40.  
  41.  
  42.  
  43. typedef struct /**Estrutura de dados correspondente aos valores das cores RGB a ser atribuídas aos vizinhos*/
  44. {
  45. float red;
  46. float green;
  47. float blue;
  48. } COR;
  49.  
  50.  
  51. typedef struct /**Estrutura de dados correspondente aos valores dos diferentes vizinhos*/
  52. {
  53. int R;
  54. int C;
  55. int E;
  56. int A;
  57. int F;
  58. int G;
  59. } VIZINHOS;
  60.  
  61.  
  62. typedef struct Reg { /**Estrutura de dados referente a leitura das regras*/
  63. char *condicao;
  64. char hipotese;
  65. struct Reg *next;
  66. } REGRA, *REGRAS;
  67.  
  68.  
  69.  
  70. int is_vazia(REGRAS r);
  71. void ver_regras(REGRAS regras);
  72. REGRAS inserir(char *condicao, char hipotese, REGRAS regras);
  73. REGRAS inverter_l(REGRAS regras);
  74.  
  75.  
  76. //Função Main
  77.  
  78. int main (int argc, char **argv)
  79. {
  80.  
  81.  
  82. if(argc != 4)
  83. { printf("\nO argumento introduzido não é permitido!\nUtilize: ./simul -[vizinhanca] [cidade] [regras]\n");
  84. return 0;
  85. }
  86.  
  87. regra = strtok(argv[1], "-"); /**Argumento que le a tipo de vizinhanca. O strtok vai remover o caracter "-"*/
  88. fmapa=argv[2]; /**Argumento que le o comando referente ao mapa a ser utilizado*/
  89. fregras=argv[3]; /**Argumento que le o comando referente as regras a serem utlizadas*/
  90.  
  91. if(!regra_valida(regra))
  92. { printf("\nRegra não permitida!\n\nRegras permitidas:\n-cruz\n-quad\n-circ\n");
  93. return 0;
  94. }
  95.  
  96. FILE *file_map = fopen(fmapa, "r");
  97. if(file_map == NULL)
  98. { fprintf(stderr, "\nErro ao abrir o ficheiro de mapa '%s'\n", fmapa);
  99. return 0;
  100. }
  101. else
  102. ler_mapa(file_map);
  103.  
  104.  
  105. /** Para manter a proporcao XLEN/YLEN */
  106. float aspect_ratio = (float) getx / (float) gety;
  107.  
  108. glutInit(&argc, argv);
  109. glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB);
  110.  
  111. /** A janela vai ter 600 de altura e o comprimento vai depender da proporcao */
  112. glutInitWindowSize(aspect_ratio * 600, 600);
  113. glutInitWindowPosition(10, 10);
  114. glutCreateWindow("Simul");
  115.  
  116. /** Inicializar o gerador de numeros aleatorios */
  117. srandom(time(NULL));
  118.  
  119. init();
  120.  
  121. /** Definir qual e a função que actualiza a janela */
  122. glutDisplayFunc(display);
  123. glutIdleFunc(display);
  124.  
  125. glutMainLoop();
  126. return 0;
  127. }
  128.  
  129.  
  130.  
  131. void init(void)
  132. {
  133. float aspect_ratio = (float) getx / (float) gety;
  134. float x = 10.0 * aspect_ratio;
  135.  
  136. glClearColor(0.0, 0.0, 0.0, 0.0);
  137. glColor3f(1.0, 1.0, 1.0);
  138. glMatrixMode(GL_PROJECTION);
  139. glLoadIdentity();
  140.  
  141. /** Qual e a janela que vemos */
  142. glOrtho(-x, x, -10.0, 10.0, -10.0, 10.0);
  143. }
  144.  
  145.  
  146.  
  147. void get_color(char estado, COR *cor) /**Funcao que vai atribuir uma determinada cor consoante o estado*/
  148. {
  149. switch (estado)
  150. { case 'R' : cor-> red = 1.00;
  151. cor-> green = 0.70;
  152. cor-> blue = 0.10;
  153. break;
  154.  
  155. case 'C' : cor-> red = 0.50;
  156. cor-> green = 0.30;
  157. cor-> blue = 0.50;
  158. break;
  159.  
  160. case 'E' : cor-> red = 0.00;
  161. cor-> green = 0.00;
  162. cor-> blue = 0.00;
  163. break;
  164.  
  165. case 'A' : cor-> red = 0.00;
  166. cor-> green = 0.50;
  167. cor-> blue = 1.00;
  168. break;
  169.  
  170. case 'F' : cor-> red = 0.00;
  171. cor-> green = 0.25;
  172. cor-> blue = 0.00;
  173. break;
  174.  
  175. case 'G' : cor-> red = 0.40;
  176. cor-> green = 0.20;
  177. cor-> blue = 0.00;
  178. break;
  179.  
  180. default : cor-> red = 0.20;
  181. cor-> green = 0.20;
  182. cor-> blue = 0.20;
  183. break;
  184. }
  185. }
  186.  
  187.  
  188.  
  189. void initialize_board(char board[XLEN][YLEN])
  190. {
  191. int i, j, k=0;
  192.  
  193. for (i=0; i<gety; i++)
  194. { for (j=0; j<getx; j++)
  195. { board[i][j] = tmp_board[k];
  196. k++;
  197. }
  198. }
  199. free(tmp_board);
  200. }
  201.  
  202.  
  203. /**
  204. * Actualizacao das celulas
  205. */
  206. void update_cell (char board[XLEN][YLEN], int x, int y)
  207. {
  208. FILE *file_rules = fopen(fregras, "r");
  209. if(file_rules == NULL)
  210. { fprintf(stderr, "\nErro ao abrir o ficheiro de regras '%s'\n", fregras);
  211. exit(1);
  212. }
  213.  
  214. ler_regra(file_rules);
  215.  
  216. }
  217.  
  218.  
  219. /**
  220. * Actualizacao do tabuleiro
  221. */
  222. void update_board(char board[XLEN][YLEN])
  223. {
  224. int x, y;
  225.  
  226. for (x = 0; x < getx; x++)
  227. for (y = 0; y < gety; y++)
  228. update_cell(board, x, y);
  229. }
  230.  
  231.  
  232. /**
  233. * Funcao que actualiza a janela e e invocada automaticamente pelo openGL
  234. */
  235. void display(void)
  236. {
  237. static int is_init = 0;
  238. static char board[XLEN][YLEN];
  239.  
  240. if(!is_init)
  241. { is_init = 1;
  242. initialize_board(board);
  243. }
  244.  
  245. glClear(GL_COLOR_BUFFER_BIT);
  246.  
  247. float aspect_ratio = (float) getx / (float) gety;
  248. float x = -10.0 * aspect_ratio;
  249. float y = 10;
  250. float dx = aspect_ratio * 20 / (float)getx;
  251. float dy = -20 / (float)gety;
  252.  
  253. int i, j;
  254.  
  255. for(j = 0; j < gety; j++)
  256. { for(i = 0; i < getx; i++)
  257. { COR cor;
  258. get_color(board[j][i], &cor);
  259.  
  260. glColor3f(cor.red, cor.green, cor.blue);
  261.  
  262. glRectf(x + i * dx, y + j * dy, x + (i + 1) * dx, y + (j + 1) * dy);
  263. }
  264. }
  265.  
  266. /** Invocar a actualização do tabuleiro */
  267. update_board(board);
  268.  
  269. glutSwapBuffers();
  270. }
  271.  
  272.  
  273. /**Funcao que limpa todos os campos referentes aos vizinhos*/
  274. void limpar_vizinhos (VIZINHOS *vizinhos)
  275. {
  276. vizinhos-> R = 0;
  277. vizinhos-> C = 0;
  278. vizinhos-> E = 0;
  279. vizinhos-> A = 0;
  280. vizinhos-> F = 0;
  281. vizinhos-> G = 0;
  282. }
  283.  
  284.  
  285. /**Funcao que calcula quantos vizinhos de cada estado uma determinada casa tem. Vizinhanca em cruz*/
  286. void viz_cruz (char board[XLEN][YLEN], int x, int y, VIZINHOS *vizinhos)
  287. {
  288. int i;
  289.  
  290. limpar_vizinhos (vizinhos);
  291.  
  292. i=-1;
  293. while(i<=1)
  294. { switch(board[x+i][y])
  295. { case 'R' : vizinhos-> R++; break;
  296. case 'C' : vizinhos-> C++; break;
  297. case 'E' : vizinhos-> E++; break;
  298. case 'A' : vizinhos-> A++; break;
  299. case 'F' : vizinhos-> F++; break;
  300. case 'G' : vizinhos-> G++; break;
  301. }
  302. i+=2;
  303. }
  304.  
  305. i=-1;
  306. while(i<=1)
  307. { switch(board[x][y+i])
  308. { case 'R' : vizinhos-> R++; break;
  309. case 'C' : vizinhos-> C++; break;
  310. case 'E' : vizinhos-> E++; break;
  311. case 'A' : vizinhos-> A++; break;
  312. case 'F' : vizinhos-> F++; break;
  313. case 'G' : vizinhos-> G++; break;
  314. }
  315. i+=2;
  316. }
  317. }
  318.  
  319.  
  320.  
  321. /**Funcao que calcula quantos vizinhos de cada estado uma determinada casa tem. Vizinhanca em quadrado*/
  322. void viz_quad (char board[XLEN][YLEN], int x, int y, VIZINHOS *vizinhos)
  323. {
  324. int i;
  325.  
  326. viz_cruz(board, x, y, vizinhos);
  327.  
  328. i=-1;
  329. while(i<=1)
  330. { switch(board[x+i][y+i])
  331. { case 'R' : vizinhos-> R++; break;
  332. case 'C' : vizinhos-> C++; break;
  333. case 'E' : vizinhos-> E++; break;
  334. case 'A' : vizinhos-> A++; break;
  335. case 'F' : vizinhos-> F++; break;
  336. case 'G' : vizinhos-> G++; break;
  337. }
  338. i+=2;
  339. }
  340.  
  341. i=-1;
  342. while(i<=1)
  343. { switch(board[x+i][y-i])
  344. { case 'R' : vizinhos-> R++; break;
  345. case 'C' : vizinhos-> C++; break;
  346. case 'E' : vizinhos-> E++; break;
  347. case 'A' : vizinhos-> A++; break;
  348. case 'F' : vizinhos-> F++; break;
  349. case 'G' : vizinhos-> G++; break;
  350. }
  351. i+=2;
  352. }
  353. }
  354.  
  355.  
  356.  
  357.  
  358. /**Funcao que calcula quantos vizinhos de cada estado uma determinada casa tem. Vizinhanca em circulo*/
  359. void viz_circ (char board[XLEN][YLEN], int x, int y, VIZINHOS *vizinhos)
  360. {
  361. int i;
  362.  
  363. viz_quad(board, x, y, vizinhos);
  364.  
  365. i=-2;
  366. while(i<=2)
  367. { switch(board[x+i][y])
  368. { case 'R' : vizinhos-> R++; break;
  369. case 'C' : vizinhos-> C++; break;
  370. case 'E' : vizinhos-> E++; break;
  371. case 'A' : vizinhos-> A++; break;
  372. case 'F' : vizinhos-> F++; break;
  373. case 'G' : vizinhos-> G++; break;
  374. }
  375. i+=4;
  376. }
  377.  
  378. i=-2;
  379. while(i<=2)
  380. { switch(board[x][y+i])
  381. { case 'R' : vizinhos-> R++; break;
  382. case 'C' : vizinhos-> C++; break;
  383. case 'E' : vizinhos-> E++; break;
  384. case 'A' : vizinhos-> A++; break;
  385. case 'F' : vizinhos-> F++; break;
  386. case 'G' : vizinhos-> G++; break;
  387. }
  388. i+=4;
  389. }
  390. }
  391.  
  392.  
  393. /**Verifica se o tipo de vizinhanca introduzida e valida*/
  394. int regra_valida(char *regra)
  395. {
  396. if (strcmp(regra, "cruz")!=0 && strcmp(regra, "quad")!=0 && strcmp(regra, "circ")!=0)
  397. return 0;
  398. else
  399. return 1;
  400. }
  401.  
  402. /**Verifica se o valor atribuido a uma determinada casa e valido*/
  403. int estado_valido(char est)
  404. {
  405. if((est != 'R') && (est != 'C') && (est != 'E') && (est != 'A') != (est == 'F') != (est == 'G'))
  406. return 0;
  407. else
  408. return 1;
  409. }
  410.  
  411.  
  412. /**Funcao que le o ficheiro referente ao mapa e atribui os valores ao board temporario*/
  413. void ler_mapa(FILE *file_map)
  414. {
  415. int i;
  416. int get[2];
  417.  
  418. for(i=0;i<2;i++)
  419. fscanf(file_map, "%d", &get[i]);
  420.  
  421. getx = get[0];
  422. gety = get[1];
  423.  
  424. if(getx>XLEN || getx<=0 || gety>YLEN || gety<=0)
  425. { printf("\nAs dimensoes da matriz nao sao permitidas!\n");
  426. exit(1);
  427. }
  428.  
  429. tmp_board = (char *) malloc(getx * gety * sizeof(char));
  430.  
  431. for (i = 0; i < (getx * gety); i++)
  432. { fscanf(file_map, "%c", &tmp_board[i]);
  433. if(isspace(tmp_board[i]))
  434. { i--;
  435. continue;
  436. }
  437. /*fscanf(file_map, "%c", &tmp_board[i]);*/
  438. if(!estado_valido(tmp_board[i]))
  439. { fprintf(stderr, "Foi encontrado um caracter invalido: ('%c')\n", tmp_board[i]);
  440. exit(1);
  441. }
  442. }
  443.  
  444. fclose(file_map);
  445. }
  446.  
  447.  
  448.  
  449. /**Funcao que le o ficheiro das regras e as armazena na struct correspondente as regras*/
  450. void ler_regra(FILE *file_rules)
  451. {
  452. int i = 0, j, x;
  453. REGRAS regras = NULL;
  454. char tmp_array[100][100];
  455. char linha[100];
  456. char ant[100][100], nvalor[100][1];
  457. char ant2[100][100], nvalor2[100][1];
  458.  
  459. while (fgets(linha, 100, file_rules) != NULL)
  460. { strcpy(tmp_array[i], linha);
  461. strcpy(ant[i], strtok(tmp_array[i], ":")); /* Antes de : */
  462. strcpy(nvalor[i], strtok(NULL, ":")); /* Depois de : */
  463. strcpy(nvalor2[i], nvalor[i]);
  464. for(j = 0; j < strlen(nvalor[i]); j++)
  465. if(isspace(nvalor[i][j]) != 0)
  466. strcpy(nvalor[i], strdelc(nvalor2[i], nvalor2[i][j]));
  467. strcpy(nvalor[i], strdelc(nvalor[i], '\n'));
  468. i++;
  469. }
  470.  
  471. for(x = 0; x < i; x++)
  472. { strcpy(ant2[x], ant[x]);
  473. for(j = 0; j < strlen(nvalor[i]); j++)
  474. if(isspace(ant[i][j]) != 0)
  475. strcpy(ant[i], strdelc(ant2[i], ant2[i][j])); /* antes do : */
  476. nvalor[i][0] = strfstc(nvalor[i]);
  477. regras = inserir(ant[i], nvalor[i][0], regras);
  478. }
  479. inverter_l(regras);
  480. fclose(file_rules);
  481. }
  482.  
  483.  
  484.  
  485. /**Funcao auxiliar para retirar o caracter finalizador '\0'*/
  486. char *strdelc (char *s, char ch)
  487. {
  488. int i,j;
  489. for(i=j=0; s[i] != '\0'; i++)
  490. if (s[i] != ch)
  491. s[j++] = s[i];
  492. s[j] = '\0';
  493. return s;
  494. }
  495.  
  496.  
  497.  
  498. /**Funcao auxiliar que vai retornar o primeiro caracter da string*/
  499. char strfstc (char *s)
  500. {
  501. return s[0];
  502. }
  503.  
  504.  
  505.  
  506. /**Insere os valores que lhe sao passados, na cabeca da lista*/
  507. REGRAS inserir(char *ant, char nvalor, REGRAS regras)
  508. {
  509. REGRAS n = (REGRAS) malloc(sizeof(REGRA));
  510. if(is_vazia(regras))
  511. { n->condicao = ant;
  512. n->hipotese = nvalor;
  513. n->next = NULL;
  514. }
  515. else
  516. { n->condicao = ant;
  517. n->hipotese = nvalor;
  518. n->next = regras;
  519. }
  520. return n;
  521. }
  522.  
  523.  
  524.  
  525. /**Verifica se a lista esta vazia*/
  526. int is_vazia(REGRAS r)
  527. {
  528. return r == NULL;
  529. }
  530.  
  531.  
  532. /**Inverte a ordem de uma lista ligada*/
  533. REGRAS inverter_l(REGRAS regras)
  534. {
  535. REGRAS n = regras;
  536. REGRAS aux = NULL;
  537. while(!is_vazia(n))
  538. { aux = inserir(n->condicao, n->hipotese, aux);
  539. n = n->next;
  540. }
  541. free(n);
  542. return aux;
  543. }
Add Comment
Please, Sign In to add comment