level.c 1.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101
  1. #include <u.h>
  2. #include <libc.h>
  3. #include <bio.h>
  4. #include <draw.h>
  5. #include "sokoban.h"
  6. void
  7. consumeline(Biobuf *b)
  8. {
  9. while(Bgetc(b) != '\n')
  10. ;
  11. }
  12. /* parse a level file */
  13. int
  14. loadlevels(char *path)
  15. {
  16. Biobuf *b;
  17. int x = 0, y = 0, lnum = 0;
  18. char c;
  19. if(path == nil)
  20. return 0;
  21. b = Bopen(path, OREAD);
  22. if(b == nil) {
  23. fprint(2, "could not open file %s: %r\n", path);
  24. return 0;
  25. }
  26. memset(levels, 0, Maxlevels*sizeof(Level));
  27. while((c = Bgetc(b)) > 0) {
  28. switch(c) {
  29. case ';':
  30. consumeline(b); /* no ';'-comments in the middle of a level */
  31. break;
  32. case '\n':
  33. levels[lnum].index = lnum;
  34. levels[lnum].done = 0;
  35. x = 0;
  36. levels[lnum].max.y = ++y;
  37. c = Bgetc(b);
  38. if(c == '\n' || c == Beof) {
  39. /* end of level */
  40. if(++lnum == Maxlevels)
  41. goto Done;
  42. x = 0;
  43. y = 0;
  44. } else
  45. Bungetc(b);
  46. break;
  47. case '#':
  48. levels[lnum].board[x][y] = Wall;
  49. x++;
  50. break;
  51. case ' ':
  52. levels[lnum].board[x][y] = Empty;
  53. x++;
  54. break;
  55. case '$':
  56. levels[lnum].board[x][y] = Cargo;
  57. x++;
  58. break;
  59. case '*':
  60. levels[lnum].board[x][y] = GoalCargo;
  61. x++;
  62. break;
  63. case '.':
  64. levels[lnum].board[x][y] = Goal;
  65. x++;
  66. break;
  67. case '@':
  68. levels[lnum].board[x][y] = Empty;
  69. levels[lnum].glenda = Pt(x, y);
  70. x++;
  71. break;
  72. case '+':
  73. levels[lnum].board[x][y] = Goal;
  74. levels[lnum].glenda = Pt(x, y);
  75. x++;
  76. break;
  77. default:
  78. fprint(2, "impossible character for level %d: %c\n", lnum+1, c);
  79. return 0;
  80. }
  81. if(x > levels[lnum].max.x)
  82. levels[lnum].max.x = x;
  83. levels[lnum].max.y = y;
  84. }
  85. Done:
  86. Bterm(b);
  87. level = levels[0];
  88. numlevels = lnum;
  89. return 1;
  90. }