Advertisement
creamygoat

Snake Game

Sep 1st, 2022 (edited)
461
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 7.83 KB | Source Code | 0 0
  1. 1 REM A silly serpent game: Works on https://www.calormen.com/jsbasic/
  2. 10 LV = 0 : HS = 0 : HL = 1 : TEXT : GOSUB 9000 : GOTO 100
  3.  
  4. 50 REM Buffer key
  5. 51 IF KN >= KS THEN RETURN
  6. 52 A = PEEK(IK%) : IF A < 128 THEN RETURN
  7. 53 POKE QK%, 0 : B = KH + KN : IF B >= KS THEN B = B - KS
  8. 54 KB%(B) = A - 128 : KN = KN + 1 : RETURN
  9.  
  10. 60 REM Extract key from buffer
  11. 61 K = 0 : IF NOT KN THEN RETURN
  12. 62 K = KB%(KH) : KN = KN - 1 : KH = KH + 1 : IF KH >= KS THEN KH = 0
  13. 63 RETURN
  14.  
  15. 70 REM Clear key buffer
  16. 71 K = 0 : KN = 0 : POKE QK%, 0 : RETURN
  17.  
  18. 100 REM New game loop (preserving high score)
  19. 110 GOSUB 7000 : REM Intro
  20. 120 SC = 0 : LV = 1 : BS = INT(H / 3) : FL = 5 : DT = 400
  21.  
  22. 200 REM Arena loop
  23. 210 GOSUB 8000 : REM BeginLevel
  24. 220 AQ = INT(0.75 * ((W - 2 * BS) * (H - 2 * BS)))
  25.  
  26. 300 REM Main loop
  27. 310 VTAB 24 : HTAB 22 : PRINT SC;
  28. 320 Z%(PX, PY) = 4 + D
  29. 330 VTAB OY + PY : HTAB OX + PX : PRINT "#";
  30. 340 GOSUB 50
  31. 350 FOR I = 1 TO DT : GOSUB 50 : NEXT
  32. 360 GOSUB 50 : GOSUB 1000 : REM Fooding
  33. 370 GOSUB 50 : GOSUB 60
  34. 380 IF K = CU AND PD <> 2 THEN PD = 0
  35. 381 IF K = CR AND PD <> 3 THEN PD = 1
  36. 382 IF K = CD AND PD <> 0 THEN PD = 2
  37. 383 IF K = CL AND PD <> 1 THEN PD = 3
  38. 390 A = PX + DX%(PD) : B = PY + DY%(PD)
  39. 400 IF A < 0 OR A >= W OR B < 0 OR B >= H THEN GOTO 900 : REM Out of bounds!
  40. 410 Z%(PX, PY) = 4 + PD : REM A breadcrumb for the tail
  41. 420 PX = A : PY = B
  42. 430 A = Z%(PX, PY)
  43. 440 IF A = 1 THEN PN = PN + 5 + INT(RND(1) * 8) : NF = NF - 1 : SC = SC + LV
  44. 450 IF A >= 4 THEN GOTO 900 : REM Collision!
  45. 460 REM Advance tail (A = 1) or allow growth (A = 0)
  46. 470 A = 1 : IF PL < PN THEN A = 0 : REM Still growing!
  47. 480 PL = PL + 1 - A
  48. 490 B = Z%(TX, TY) : F = (1 - A) * B
  49. 500 Z%(TX, TY) = F : EX%(NE) = TX : EY%(NE) = TY
  50. 510 IF NOT F THEN NE = NE + 1 : REM Add to the pool of empty spaces.
  51. 520 VTAB OY + TY : HTAB OX + TX : PRINT MID$(WM$, 1 + A, 1);
  52. 530 B = B - 4 : TX = TX + A * DX%(B) : TY = TY + A * DY%(B)
  53. 540 IF PL >= AQ THEN GOTO 800 : REM Awesome victory!
  54. 550 GOSUB 50
  55. 560 GOTO 300
  56.  
  57. 800 REM Screen mostly filled with snake!
  58. 820 HOME
  59. 830 LV = LV + 1
  60. 831 A = INT(0.9 * DT)
  61. 832 B = DT : IF LV = 5 * INT(LV / 5) THEN B = DT - 1
  62. 833 IF DT < 20 THEN A = B
  63. 833 DT = A
  64. 834 IF DT < 0 THEN DT = 0
  65. 840 IF LV = 3 * INT(LV / 3) THEN FL = FL - 1 : IF FL < 1 THEN FL = 1
  66. 845 IF LV = 2 * INT(LV / 2) THEN BS = BS - 1 : IF BS < 1 THEN BS = 1
  67. 850 SC = SC + 10 * LV
  68. 860 GOSUB 4000 : REM DispLabels
  69. 861 VTAB 24 : HTAB 22 : PRINT SC;
  70. 870 S0$ = "LEVEL " + STR$(LV - 1) + " COMPLETED"
  71. 871 S1$ = "````Doom awaits you in``LEVEL " + STR$(LV)
  72. 872 S2$ = "````PRESS ANY KEY"
  73. 880 GOSUB 7500 : GOSUB 5000
  74. 890 GOTO 200
  75.  
  76. 900 REM Doom and giblets for Dogar and Kazon
  77. 910 VTAB OY + PY : HTAB OX + PX : PRINT "*"
  78. 920 GOSUB 3000 : REM Drama
  79. 930 GOSUB 3500 : REM SprayGiblets
  80. 940 IF SC = HS THEN IF LV > HL THEN HL = LV
  81. 950 IF SC > HS THEN HS = SC : HL = LV
  82. 960 GOTO 100
  83.  
  84. 1000 REM SUB Fooding
  85. 1010 FOR I = 1 TO 2
  86. 1020 IF NE < 1 THEN RETURN
  87. 1030 C = INT(RND(1) * NE) : A = EX%(C) : B = EY%(C)
  88. 1040 E = 0 : F = Z%(A, B)
  89. 1050 IF F = 0 AND NF < FL THEN E = 1 : F = 1 : NF = NF + 1
  90. 1060 Z%(A, B) = F : IF F THEN F = 1
  91. 1070 A = A + OX : B = B + OY
  92. 1080 S$ = "o": IF NOT E THEN A = 1 : B = DH : S$ = " "
  93. 1090 IF NOT F THEN C = NE - 1
  94. 1100 EX%(C) = EX%(NE - 1) : EY%(C) = EY%(NE - 1) : NE = NE - F
  95. 1110 VTAB B : HTAB A : PRINT S$;
  96. 1120 NEXT
  97. 1130 RETURN
  98.  
  99. 1500 REM SUB ClearArena
  100. 1510 NE = 0
  101. 1515 FOR I = 0 TO W - 1 : FOR J = 0 TO H - 1 : Z%(I, J) = 8 : NEXT : NEXT
  102. 1520 FOR I = BS TO W - BS - 1 : FOR J = BS TO H - BS - 1
  103. 1525 Z%(I, J) = 0 : EX%(NE) = I : EY%(NE) = J : NE = NE + 1
  104. 1530 NEXT : NEXT
  105. 1540 REM Player (with tail)
  106. 1550 PD = 1 + 2 * INT(2 * RND(1))
  107. 1560 PX = INT(W / 2) - INT((W - 2 * BS) / 3) * DX%(PD)
  108. 1561 PY = INT(H / 2) - INT((H - 2 * BS) / 3) * DY%(PD)
  109. 1570 TX = PX : TY = PY
  110. 1580 PL = 1 : PN = 10 + 2 * LV
  111. 1590 REM Food
  112. 1600 NF = 0
  113. 1610 RETURN
  114.  
  115. 3000 REM SUB BeginDrama(PX, PY)
  116. 3010 S$ = "@ #.* +#" : A = 0
  117. 3020 FOR I = 1 TO 600
  118. 3030 VTAB OY + PY : HTAB OX + PX : PRINT MID$(S$, A, 1)
  119. 3040 A = A + 1 : IF A >= 8 THEN A = 0
  120. 3050 NEXT I
  121. 3060 RETURN
  122.  
  123. 3500 REM SUB SprayGiblets(PX, PY)
  124. 3550 FOR I = 0 TO NG - 1 : GX(I) = OX + PX : GY(I) = OY + PY : NEXT
  125. 3560 FOR I = 0 TO NG - 1
  126. 3561 B = RND(1) * 2 * PI : A = RND(1): A = 1.3 + 7 * A * A
  127. 3562 VX(I) = A * COS(B) : VY(I) = A * SIN(B) - 2.0
  128. 3563 NEXT
  129. 3570 FOR J = 1 TO 35
  130. 3580 FOR I = 0 TO NG - 1
  131. 3590 A = INT(GX(I)) : B = INT(GY(I))
  132. 3600 GX(I) = GX(I) + VX(I) : GY(I) = GY(I) + VY(I) : VY(I) = VY(I) + 0.7
  133. 3610 IF A >= 1 AND A <= DW AND B >= 1 AND B < DH THEN VTAB B : HTAB A : PRINT ".";
  134. 3620 A = INT(GX(I)) : B = INT(GY(I))
  135. 3630 IF A >= 1 AND A <= DW AND B >= 1 AND B < DH THEN VTAB B : HTAB A : PRINT "*";
  136. 3640 NEXT
  137. 3650 NEXT
  138. 3660 RETURN
  139.  
  140. 4000 REM SUB DispLabels(LV, HS)
  141. 4010 VTAB DH
  142. 4015 HTAB 4 : PRINT "Level " + STR$(LV);
  143. 4020 HTAB INT((DW - 8) / 2) : PRINT "Score";
  144. 4025 HTAB DW - 11 : PRINT "Best " + STR$(HS);
  145. 4050 RETURN
  146.  
  147. 4500 REM DispArena
  148. 4550 FOR J = 0 TO H - 1
  149. 4551 FOR I = 0 TO W - 1
  150. 4552 VTAB OY + J : HTAB OX + I
  151. 4553 A = Z%(I, J)
  152. 4554 IF A = 8 THEN PRINT "X";
  153. 4555 IF A <> 8 THEN PRINT " ";
  154. 4560 NEXT
  155. 4561 NEXT
  156. 4570 RETURN
  157.  
  158. 5000 REM WaitForKey
  159. 5010 GOSUB 70
  160. 5020 GOSUB 50 : GOSUB 60 : IF K = 0 GOTO 5020
  161. 5030 GOSUB 70
  162. 5040 RETURN
  163.  
  164. 7000 REM Intro
  165. 7010 S0$ = "DELUXE PROFESSIONAL SNAKE SIMULATOR```Be a snake. Do snake things."
  166. 7011 S0$ = S0$ + "`Try not to explode.````CONTROLS``"
  167. 7012 S0$ = S0$ + CHR$(CU) + ": Up` "
  168. 7013 S0$ = S0$ + CHR$(CL) + ": Left "
  169. 7014 S0$ = S0$ + CHR$(CD) + ": Down "
  170. 7015 S0$ = S0$ + CHR$(CR) + ": Right"
  171. 7020 S1$ = "```Last score: " + STR$(SC) + ", Level " + STR$(LV) + ""
  172. 7022 S1$ = S1$ + "``Best score: " + STR$(HS) + ", Level " + STR$(HL) + ""
  173. 7023 IF LV < 1 THEN S1$ = "`````"
  174. 7025 S2$ = "```PRESS ANY KEY TO BEGIN!"
  175. 7030 HOME : GOSUB 7500 : GOSUB 5000
  176. 7390 RETURN
  177.  
  178. 7500 REM ShowMsg(S0$, S1$, S2$)
  179. 7510 C = 0
  180. 7520 FOR I = 0 TO 2
  181. 7521 S$ = S0$ : IF I THEN S$ = S1$ : IF I = 2 THEN S$ = S2$
  182. 7522 FOR J = 1 TO LEN(S$)
  183. 7523 IF LEN(S$) > 0 THEN IF MID$(S$, J, 1) = "`" THEN C = C + 1
  184. 7524 NEXT
  185. 7525 IF LEN(S$) > 0 THEN C = C + 1
  186. 7526 NEXT
  187. 7527 D = INT((24 - C) / 2 + 0.5)
  188. 7530 FOR I = 0 TO 2
  189. 7540 A = 1 : S$ = S0$ : IF I THEN S$ = S1$ : IF I = 2 THEN S$ = S2$
  190. 7550 B = LEN(S$) + 1
  191. 7560 FOR J = 0 TO LEN(S$) - A
  192. 7561 IF MID$(S$, LEN(S$) - J, 1) = "`" THEN B = LEN(S$) - J
  193. 7562 NEXT
  194. 7570 C = INT((40 + A - B) / 2)
  195. 7580 IF C < 1 THEN PRINT : PRINT MID$(S$, A, B - A) : PRINT "TOO LONG!" : STOP
  196. 7590 IF B >= A THEN VTAB D : HTAB C : PRINT MID$(S$, A, B - A);
  197. 7600 D = D + 1 : A = B + 1
  198. 7610 IF A <= LEN(S$) GOTO 7550
  199. 7620 NEXT
  200. 7630 RETURN
  201.  
  202. 8000 REM BeginLevel
  203. 8010 HOME
  204. 8020 GOSUB 1500 : REM ClearArena
  205. 8030 GOSUB 4000 : REM DispLabels
  206. 8040 GOSUB 4500 : REM DispArena
  207. 8050 RETURN
  208.  
  209. 9000 REM SUB Initialisation
  210. 9010 PI = 3.1415926535897932384626433832795
  211. 9015 DW = 40 : DH = 24 : REM Display width and height
  212. 9020 REM Board, containing breadcrumbs
  213. 9021 W = 24 : H = 20
  214. 9022 OX = 1 + INT((DW - W) / 2) : OY = 1 + INT((DH - H) / 2)
  215. 9023 DIM Z%(W - 1, H - 1)
  216. 9030 REM Directions and unit displacements
  217. 9040 DIM DX%(3), DY%(3)
  218. 9042 DX%(0) = 0 : DY%(0) = -1
  219. 9043 DX%(1) = 1 : DY%(1) = 0
  220. 9044 DX%(2) = 0 : DY%(2) = 1
  221. 9045 DX%(3) = -1 : DY%(3) = 0
  222. 9050 REM IO addresses
  223. 9060 IK% = -16384 : QK% = -16368
  224. 9070 REM Giblets
  225. 9080 NG = 60
  226. 9090 DIM GX(NG - 1), GY(NG - 1), VX(NG - 1), VY(NG - 1)
  227. 9100 REM Pool of candidate empty spaces
  228. 9110 DIM EX%(W * H - 1), EY%(W * H - 1) : NE = 0
  229. 9120 REM Keyboard ring buffer
  230. 9130 KS = 8 : DIM KB%(KS - 1) : KH = 0 : KN = 0
  231. 9140 REM Scripted key sequence
  232. 9150 VP = 0 : VQ = 0 : VT = 0 : RESTORE
  233. 9160 REM Key bindings
  234. 9170 CU = ASC("W") : CL = ASC("A") : CD = ASC("S") : CR = ASC("D")
  235. 9180 REM Display options
  236. 9190 WB$ = "#" : REM Body
  237. 9191 WC$ = " " : REM Worm castings (" " or "." works well.)
  238. 9192 WF$ = "o" : REM Adorable furry animal
  239. 9200 WM$ = WB$ + WC$
  240. 9210 REM Remember to call ClearArea
  241. 9220 RETURN
  242.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement