home *** CD-ROM | disk | FTP | other *** search
/ ARM Club 1 / ARM_CLUB_CD.iso / contents / apps / languages / progs / curses / examples / c / mwalls < prev    next >
Encoding:
Text File  |  1991-11-16  |  5.8 KB  |  284 lines

  1. /*                                                *
  2.  *             M A G I C   W A L L S              *
  3.  *                                                *
  4.  *     mwalls.c                                   *
  5.  *     Heikki Suopanki 1991                       *
  6.  *     email: suopanki@phoenix.oulu.fi            *
  7.  *                                                *
  8.  *     You are a ghost, you have to go through    *
  9.  *     every wall once and only once.             *
  10.  *                                                */
  11.  
  12. #include <stdio.h>
  13. #include <curses.h>
  14.  
  15. #define XMAX 35
  16. #define XMIN 5
  17. #define YMAX 22
  18. #define YMIN 2
  19. #define THICK 1
  20. #define THIN 0
  21. #define START_PLACES 6
  22. #define THICK_WALL "#"
  23. #define THIN_WALL  "+"
  24. #define GHOST "%"
  25. #define WALL_NUM   16
  26. #define NORMAL_MOVE -1
  27. #define CANT_MOVE 100
  28.  
  29.  
  30. int xp, xpo, yp, ypo;
  31. int walls;
  32. int moves;
  33.  
  34. struct wall_pos {
  35.   int x_start;
  36.   int y_start;
  37.   int x_end;
  38.   int y_end;
  39.   int wall_state;
  40. } ;
  41.  
  42. struct wall_pos wall_map[WALL_NUM] =
  43. {
  44.   {10,7,15,7,THIN},
  45.   {15,7,25,7,THIN},
  46.   {25,7,30,7,THIN},
  47.   {15,12,20,12,THIN},
  48.   {20,12,25,12,THIN},
  49.   {25,12,30,12,THIN},
  50.   {10,17,15,17,THIN},
  51.   {15,17,20,17,THIN},
  52.   {20,17,30,17,THIN},
  53.   {10,7,10,17,THIN},
  54.   {15,7,15,12,THIN},
  55.   {15,12,15,17,THIN},
  56.   {20,12,20,17,THIN},
  57.   {25,7,25,12,THIN},
  58.   {30,7,30,12,THIN},
  59.   {30,12,30,17,THIN}
  60. };
  61.  
  62. int start_place[START_PLACES][2] =
  63. { 20, 5, 12, 12, 20, 10, 27, 10, 17, 15, 25, 15};
  64.  
  65. main(argc,argv)
  66. int argc;
  67. char *argv[];
  68. {
  69.   char mv;
  70.   if (argc>1) show_instructions();
  71.   init_game();
  72.   while(walls > 0) {
  73.     mv = getch();
  74.     if (mv == 'q' || mv == 'Q') end_game(); 
  75.     if (mv == 'r'){
  76.       redraw_screen();
  77.       move_player();
  78.     }
  79.     if (mv == 'n') init_game();
  80.     if (mv == 'h' || mv == 'j' || mv == 'k' || mv == 'l') {
  81.       xpo = xp;
  82.       ypo = yp;
  83.       moves++;
  84.       if (mv == 'h') {
  85.     if (--xp < XMIN) xp = XMIN; }
  86.         if (mv == 'j') {
  87.     if (++yp > YMAX) yp = YMAX; }
  88.       if (mv == 'k') {
  89.     if (--yp < YMIN) yp = YMIN; }
  90.       if (mv == 'l') {
  91.     if (++xp > XMAX) xp = XMAX; }
  92.       update_game();
  93.       move_player();
  94.     }
  95.   }
  96.   clear();
  97.   refresh();
  98.   endwin();
  99.   printf("%s", "Congratulations!");
  100.   printf("%s%d%s", "You solved the game using ", moves, " moves");
  101.   exit(); 
  102.                                      
  103. }
  104.  
  105. init_game()
  106. {
  107.   int place;
  108.   int i;
  109.   for(i=0;i < WALL_NUM; i++){
  110.     wall_map[i].wall_state = THIN;
  111.   }
  112.   moves = 0;  
  113.   walls = WALL_NUM;
  114.   initscr();
  115.   crmode();
  116.   noecho();
  117.   xp = 10;
  118.   xpo = xp;
  119.   yp = 3;
  120.   ypo = yp;
  121.   redraw_screen();
  122.   for(i=0; i < START_PLACES; i++){
  123.     mvprintw(start_place[i][1], start_place[i][0],"%1d", i+1);
  124.   }
  125.   mvaddstr(20, 40, "Starting place? Give number (1-6)");
  126.   refresh();
  127.   place = 0;
  128.   while (place < 1 || place > START_PLACES){
  129.     place = getch() - 48;
  130.   }
  131.   mvaddstr(20, 40, "                                  ");
  132.   for(i=0; i < START_PLACES; i++){
  133.     mvaddstr(start_place[i][1], start_place[i][0], " ");
  134.   }
  135.   xp = start_place[--place][0];
  136.   yp = start_place[place][1];
  137.   move_player();
  138. }
  139.  
  140. update_game()
  141. {
  142.   int check_res;
  143.   check_res = check_wall();
  144.   if (check_res == CANT_MOVE) {
  145.     xp = xpo;
  146.     yp = ypo;
  147.   }  
  148.   else {
  149.     if (check_res != NORMAL_MOVE) {
  150.       xp = 2*xp - xpo; 
  151.       yp = 2*yp - ypo; 
  152.       move_player();
  153.       block_wall(check_res);
  154.     }
  155.   }
  156.   update_stats();
  157. }
  158.  
  159. redraw_screen()
  160. {
  161.   int i,x1,y1,x2,y2;
  162.   char *wall_type;
  163.   clear();
  164.   for(i=0; i < WALL_NUM; i++) {
  165.     x1 = wall_map[i].x_start;              
  166.     y1 = wall_map[i].y_start;
  167.     x2 = wall_map[i].x_end;
  168.     y2 = wall_map[i].y_end;
  169.     if (wall_map[i].wall_state == THICK){
  170.       wall_type = THICK_WALL;
  171.     }
  172.     else {
  173.       wall_type = THIN_WALL;
  174.     }
  175.     if (x1 == x2) {
  176.       while (y1 <= y2) {
  177.     mvaddstr(y1++,x1, wall_type);
  178.       }
  179.     }
  180.     else {
  181.       while (x1 <= x2) {
  182.     mvaddstr(y1,x1++, wall_type);
  183.       }
  184.     }
  185.   }
  186.   mvaddstr(1,6, " M A G I C   W A L L S  v1.0 , Heikki Suopanki 1991.");
  187.   mvaddstr(3, 50, "Solve the puzzle....");
  188.   mvaddstr(4, 50, "Go through each wall!");
  189.   mvprintw(8, 50, "%s%3d", "Moves:      ", moves);
  190.   mvprintw(9, 50, "%s%3d", "Walls left: ", walls);
  191.   mvaddstr(12, 55, "k");
  192.   mvaddstr(13, 53, "h   l");
  193.   mvaddstr(14, 55, "j");
  194.   mvaddstr(15, 50, "r = redisplay");
  195.   mvaddstr(16, 50, "n = new game");
  196.   mvaddstr(17, 50, "q = quit");
  197.   move(yp, xp);
  198.   refresh();
  199. }
  200.  
  201. check_wall()
  202. {
  203.   int i;
  204.   int sum = 0;
  205.   int result = NORMAL_MOVE;
  206.   for(i=0; i < WALL_NUM;i++) {
  207.     if (wall_map[i].x_start == wall_map[i].x_end) {
  208.       if (xp == wall_map[i].x_start && yp >= wall_map[i].y_start && yp <= wall_map[i].y_end) {
  209.     if (wall_map[i].wall_state == THIN){
  210.       result = i; }
  211.     else { result = CANT_MOVE;}
  212.     sum++;
  213.       }     
  214.     }
  215.     else {
  216.       if (yp == wall_map[i].y_start && xp >= wall_map[i].x_start && xp <= wall_map[i].x_end) {
  217.     if (wall_map[i].wall_state == THIN){
  218.       result = i; }
  219.     else { result = CANT_MOVE;}
  220.     sum++;
  221.       }
  222.     }
  223.     
  224.   }
  225.   if (sum > 1) { result = CANT_MOVE;}
  226.   return result;
  227. }
  228.  
  229. move_player()
  230. {
  231.   mvaddstr(ypo,xpo, " ");
  232.   mvaddstr(yp,xp, GHOST);
  233.   move(yp,xp);
  234.   refresh();
  235. }
  236.  
  237. update_stats()
  238. {
  239.   mvprintw(8, 62, "%3d", moves);
  240.   mvprintw(9, 62, "%3d", walls);
  241. }
  242.  
  243. show_instructions()
  244. {
  245.   puts("You are a ghost and you have to go through every wall.");
  246.   puts("You can go only once through each wall.");
  247.   puts("The walls are marked either ++++ or ###, depending on");
  248.   puts("whether you have go through them or not.");
  249.   puts("You can choose the room where you want to start.");
  250.   exit();
  251. }
  252.  
  253. block_wall(i)
  254. int i;
  255. {
  256.   int x1,y1,x2,y2;
  257.   wall_map[i].wall_state = THICK;
  258.   walls--;
  259.   x1 = wall_map[i].x_start;
  260.   y1 = wall_map[i].y_start;
  261.   x2 = wall_map[i].x_end;
  262.   y2 = wall_map[i].y_end;
  263.   if (x1 == x2) {
  264.     while (y1 <= y2) {
  265.       mvaddstr(y1++,x1, "#");
  266.     }
  267.   }
  268.   else {
  269.     while (x1 <= x2){
  270.       mvaddstr(y1,x1++, "#");
  271.     }
  272.   }
  273. }
  274.  
  275. end_game()
  276. {
  277.   clear(); 
  278.   mvaddstr(20,1, "");
  279.   refresh();
  280.   endwin();
  281.   printf("\n");
  282.   exit();
  283. }
  284.