Addendum: A Final Fix
It's true, our previous episode was the last one, but there's a little bug to be fixed. — A qestion of honour.
Tiny Little Walls
There aren't just tiny little passages in our maze, also, from time to time, we'll hit a wall in front of us. And here it is, where our little application doesn't do exactly what we expected it to do. And we won't leave this project as-is with this little bug, just because Retrochallenge 2016/01 is over.
So, what's it all about? Most dungeon crawlers are drawing walls simply as unit segments, each one separated from the next one by an edge. Not so Maze War: Here, adjacent wall segements are mended into a single, continuous wall. This works fine in our little game, but there's an edge case regarding a junction right where we hit a wall in front of us. It's here, where our program became a little confused about when to draw and when not to draw an edge.
This is what we have to deal with and how we want it to be drawn onto the screen:
At closer inspection, there are just 3 types of how a frontal wall may connect at either side to the rest of the scene as rendered in the viewport. We introduced code 4 for the edge case concerning a junction to the side and ahead, and get the following codes for this (code 1 represents a passage, a 2 OR-ed represents a corner, 4 is a junction):
So, there are two possible parts of our program that may cause the trouble: Either, we get the encoding wrong where we collect the view-path info, or we get it wrong when we render a frontal wall and its adjacent sides.
Let's check the encoding first. We'll insert a line printing a debug message below the maze map, just at the end of the code for collecting the view-path information:
1645 IF W0>CM THEN PRINT CHR$(ES);"Y";CHR$(EB+C7);CHR$(EB+22);VL(W0);VR(W0); ELSE PRINT CHR$(ES);"Y";CHR$(EB+C7);CHR$(EB+22);" ";
Turns out, the encoding is correct. Thus, we may conclude, the bug is somewhere in the rendering routine. It concerns the right side only (so no debugging with Virtual T, since there is no support for display offset decrements, as required for writing from right to left; that's also, why we didn't manage to catch this bug in the first place) — and it concerns only codes 1 and 2:
So this must be the culprit:
122 REM handle right side
124 IF VR(W0)=C4 THEN 136
126 VM=VR(W0) AND C1:VE=VL(W0) AND C2
128 FOR VS=C2 TO C3:OUT PA,PV(VS)
130 FOR K=VI(VS,W0,VM,C0) TO VI(VS,W0,VM,C1) STEP C3
132 ON VK(K) GOSUB 31,32,33,34
134 NEXT:NEXT:GOTO 148
136 VE=C1:REM passage to the right and ahead
138 FOR VS=C2 TO C3:OUT PA,PV(VS)
140 FOR K=VI(VS,W0,C1,C0) TO VI(VS,W0,C1,C1) STEP C3
142 ON VK(K) GOSUB 31,36,37,34
144 NEXT:NEXT
146 REM finally draw the wall
148 (...)
After staring at the code for a while (no, there isn't a magical red mark-up in the original), we detect a stupid copy'n'paste error in line 126, where we refer to the left side, as in "VL", instead of the right one, "VR". — Fixed easily, phew!
126 VM=VR(W0) AND C1:VE=VR(W0) AND C2
And this is what we get (no erroneous edge drawn anymore on the wall leading to the passage at the far right):
— As it turns out, this entire post is about a single letter ("R" as in "VR"). :-)
Here is our final program, legible version including spaces (slow, for a suitable runtime version see the listing below):
10 REM Maze War Dungeon Roamer (final), N.Landsteiner 01/2016 20 DEFSNG A:DEFINT B-Z:SCREEN 0,0:CLS:PRINT"Setting up...":GOTO 200 35 REM == time critical subroutines == 30 REM viewport draw commands 31 OUT PC,VK(K+C1):RETURN 32 B=VK(K+C2):FOR J=C0 TO VK(K+C1):OUT PD,B:NEXT:RETURN 33 FOR J=VK(K+C1) TO VK(K+C2):OUT PD,BL(J):NEXT:RETURN 34 IF VE THEN OUT PD,VK(K+C1) ELSE OUT PD,VK(K+C2) 35 RETURN 36 FOR J=C0 TO VK(K+C1):OUT PD,C0:NEXT:RETURN 37 FOR J=VK(K+C1) TO VK(K+C2):OUT PD,C0:NEXT:RETURN 39 REM subroutine: render-viewport 40 ON G GOSUB 910,920,930,930,940 42 OUT PB,C0 44 OUT PA,PL:OUT PC,PU:OUT PA,PR:OUT PC,PQ 46 FOR I=C0 TO C7 48 IF W0=I THEN GOSUB 100:I=C7:GOTO 76 50 IF W1=I THEN GOSUB 90 52 IF VL(I)=HL(I) THEN 64 54 VM=VL(I) AND C1:VE=VL(I) AND C2 56 FOR VS=C0 TO C1:OUT PA,PV(VS) 58 FOR K=VI(VS,I,VM,C0) TO VI(VS,I,VM,C1) STEP C3 60 ON VK(K) GOSUB 31,32,33,34 62 NEXT:NEXT 64 IF VR(I)=HR(I) THEN 76 66 VM=VR(I) AND C1:VE=VR(I) AND C2 68 FOR VS=C2 TO C3:OUT PA,PV(VS) 70 FOR K=VI(VS,I,VM,C0) TO VI(VS,I,VM,C1) STEP C3 72 ON VK(K) GOSUB 31,32,33,34 74 NEXT:NEXT 76 NEXT 78 FOR I=C0 TO C7:HL(I)=VL(I):HR(I)=VR(I):NEXT:W1=W0 80 OUT PA,PR:OUT PC,PU 82 ON G GOSUB 960,970,980,980,990 84 RETURN 89 REM erase a wall 90 IF W1=C7 THEN RETURN 92 FOR VS=C0 TO C3:OUT PA,PV(VS):K=VI(VS,W1,C2,C0):OUT PC,VK(K+C1) 94 FOR J=C0 TO VK(K+C4):OUT PD,C0:NEXT 96 NEXT:RETURN 98 REM draw blocking wall; handle left side 100 IF VL(W0)=C4 THEN 112 102 VM=VL(W0) AND C1:VE=VL(W0) AND C2 104 FOR VS=C0 TO C1:OUT PA,PV(VS) 106 FOR K=VI(VS,W0,VM,C0) TO VI(VS,W0,VM,C1) STEP C3 108 ON VK(K) GOSUB 31,32,33,34 110 NEXT:NEXT:GOTO 124 112 VE=C1:REM passage to the left and ahead 114 FOR VS=C0 TO C1:OUT PA,PV(VS) 116 FOR K=VI(VS,W0,C1,C0) TO VI(VS,W0,C1,C1) STEP C3 118 ON VK(K) GOSUB 31,36,37,34 120 NEXT:NEXT 122 REM handle right side 124 IF VR(W0)=C4 THEN 136 126 VM=VR(W0) AND C1:VE=VL(W0) AND C2 128 FOR VS=C2 TO C3:OUT PA,PV(VS) 130 FOR K=VI(VS,W0,VM,C0) TO VI(VS,W0,VM,C1) STEP C3 132 ON VK(K) GOSUB 31,32,33,34 134 NEXT:NEXT:GOTO 148 136 VE=C1:REM passage to the right and ahead 138 FOR VS=C2 TO C3:OUT PA,PV(VS) 140 FOR K=VI(VS,W0,C1,C0) TO VI(VS,W0,C1,C1) STEP C3 142 ON VK(K) GOSUB 31,36,37,34 144 NEXT:NEXT 146 REM finally draw the wall 148 IF W0=C7 THEN RETURN 150 FOR VS=C0 TO C3:OUT PA,PV(VS) 152 FOR K=VI(VS,W0,C2,C0) TO VI(VS,W0,C2,C1) STEP C3 154 ON VK(K) GOSUB 31,32,33,34 156 NEXT:NEXT 158 RETURN 160 REM == setup, execution starts here == 195 REM G: 1=PC-8201A, 2=M10 (w/o modem), 3=Model 100, 4=Model 102, 5=KC85 200 B=PEEK(1):G= -(B=148) -(B=35)*2 -(B=51)*3 -(B=167)*4 -(B=225)*5 205 IF G=0 THEN SCREEN 0,1:PRINT "Sorry, model not supported. Gestalt:";B:END 210 IF G=1 THEN AK=65128! ELSE IF G=2 THEN AK=65389! ELSE IF G=5 THEN AK=65387! ELSE AK=65450! 215 C0=0:C1=1:C2=2:C3=3:C4=4:C5=5:C6=6:C7=7:C8=8:C9=9 220 CA=10:CC=12:CE=14:CN=49:CL=50:CP=64:CM=-1 225 UC=223:LC=97:CK=27:ES=27:EB=32:E8=17 230 PA=185:PB=186:PC=254:PD=255:DIM SA(9),SB(9):SG=-1:SH=0 235 FOR I=C0 TO C9:READ B1,B2:SA(I)=B1:SB(I)=B2:NEXT 240 DX=0:DY=0:DIM DX(3),DY(3):FOR I=C0 TO C3:READ B1,B2:DX(I)=B1:DY(I)=B2:NEXT 245 DL=0:DR=0:DIM DL(3),DR(3) 250 FOR I=C0 TO C3:READ B:DL(I)=B:NEXT 255 FOR I=C0 TO C3:READ B:DR(I)=B:NEXT 260 DIM DD(3):FOR I=C0 TO C3:READ B:DD(I)=B:NEXT 269 REM setup the maze 270 DIM SM(3,3,2):FOR I=C0 TO C3:FOR Y=C0 TO C3:READ B1,B2:SM(I,Y,C1)=B1:SM(I,Y,C0)=B2:NEXT:NEXT 275 DIM ST(3,1,1):FOR I=C0 TO C3:FOR Y=C0 TO C1:READ B1,B2:ST(I,Y,C1)=B1:ST(I,Y,C0)=B2:NEXT:NEXT 280 MW=31:MH=15:ML=132:MT=5:DIM M(MH,MW),BM(C9) 285 FOR Y=C0 TO C9:READ B:BM(Y)=B:NEXT 290 FOR Y=C0 TO MH:FOR X=C0 TO MW:READ B:M(Y,X)=B:NEXT:NEXT 295 GOSUB 1010:GOSUB 1110:REM setup viewport 299 REM == main == 300 CLS:GOSUB 700:MX=11:MY=7:MD=0:DX=DX(MD):DY=DY(MD):DL=DL(MD):DR=DR(MD) 310 PRINT CHR$(ES);"Y";CHR$(EB+C7);CHR$(EB+22);"Crsr,IJKL,Q:quit"; 315 GOSUB 460:GOSUB 1770:GOSUB 1510:GOSUB 40 319 REM main loop 320 B=PEEK(AK):IF B=C0 THEN 320 330 K=PEEK(AK+B):POKE AK,C0:IF K>CK THEN ON K-CK GOTO 500,520,540,560 340 IF K>=LC THEN K=K AND UC 350 ON INSTR("JLKI Q",CHR$(K)) GOTO 520,500,560,540,580,590 360 GOTO 320 398 REM == subroutines == 399 REM segement/pos select 400 SH=SG:SG=SX\CL:IF SY>C3 THEN SG=SG+C5 410 IF (SG<>SH) THEN OUT PA,SA(SG):OUT PB,SB(SG) 420 OUT PC,(SY MOD C4)*CP OR SX MOD CL:RETURN 449 REM clear/draw marker 450 X=ML+MX*C3:Y=MT+MY*C3:FOR I=C0 TO C3:PRESET(X+SM(MD,I,C0),Y+SM(MD,I,C1)):NEXT:RETURN 460 X=ML+MX*C3:Y=MT+MY*C3:FOR I=C0 TO C3:PSET(X+SM(MD,I,C0),Y+SM(MD,I,C1)):NEXT:RETURN 470 X=ML+MX*C3:Y=MT+MY*C3:PRESET(X+ST(MD,T0,C0),Y+ST(MD,T0,C1)):PSET(X+ST(MD,T1,C0),Y+ST(MD,T1,C1)):RETURN 499 REM key handling (right, left, bkwd, fwd, fire, quit) 500 T0=C1:T1=C0:GOSUB 470:MD=DR:DX=DX(MD):DY=DY(MD):DL=DL(MD):DR=DR(MD):GOTO 610 520 MD=DL:T0=C0:T1=C1:GOSUB 470:DX=DX(MD):DY=DY(MD):DL=DL(MD):DR=DR(MD):GOTO 610 540 GOSUB 450:MX=MX+DX:MY=MY+DY:IF M(MY,MX)=C0 THEN MX=MX-DX:MY=MY-DY:GOSUB 460:GOTO 320 550 GOSUB 460:GOTO 610 560 GOSUB 450:MX=MX-DX:MY=MY-DY:IF M(MY,MX)=C0 THEN MX=MX+DX:MY=MY+DY:GOSUB 460:GOTO 320 570 GOSUB 460:GOTO 610 580 GOTO 320:REM shoot 590 SCREEN 0,1:CLS:PRINT"- Bye -":END 600 REM view port: get path and display it 610 GOSUB 1510:GOSUB 40:GOTO 320 699 REM maze display 700 SY=MT\C8:Y0=0:D=MT MOD C8+C2:ON G GOSUB 910,920,930,930,940 710 Y1=Y0+C1:Y2=Y0+C2:Y3=Y0+C3:B0=BM(D) 720 IF (Y1<=MH) AND (D<C7) THEN B1=BM(D+C3) ELSE B1=C0 730 IF (Y2<=MH) AND (D<C4) THEN B2=BM(D+C6) ELSE B2=C0 740 IF (Y3<=MH) AND (D=C0) THEN B3=BM(D+C9) ELSE B3=C0 750 SX=ML:GOSUB 400 760 FOR MX=C0 TO MW:IF M(Y0,MX)=C0 THEN B=B0 ELSE B=C0 770 IF B1 THEN IF M(Y1,MX)=C0 THEN B=B OR B1 780 IF B2 THEN IF M(Y2,MX)=C0 THEN B=B OR B2 790 IF B3 THEN IF M(Y3,MX)=C0 THEN B=B OR B3 800 FOR I=C0 TO C2:IF SX MOD CL=C0 THEN GOSUB 400 810 OUT PD,B:SX=SX+C1:NEXT:NEXT 820 Y0=Y0+(CA-D)\C3:IF Y0>MH THEN 840 830 D=(D+C1)MOD C3:SY=SY+C1:GOTO 710 840 ON G GOSUB 960,970,980,980,990:RETURN 900 REM disable interrupts 910 EXEC 30437:RETURN 920 CALL 29558:RETURN 930 CALL 30300:RETURN 940 CALL 29450:RETURN 950 REM enable interrupts 960 EXEC 29888:RETURN 970 CALL 28998:RETURN 980 CALL 29756:RETURN 990 CALL 28906:RETURN 1000 REM setup viewport 1010 PL=33:PR=66:REM LCD blocks 0+5, 1+6 1020 PU=59:PQ=58:REM LCD counter setting increment/decrement 1030 DIM PV(3):FOR I=0 TO 3:READ B:PV(I)=B:NEXT 1040 DIM BL(29):FOR I=0 TO 29:READ B:BL(I)=B:NEXT 1050 DIM BP(33):FOR I=0 TO 33:READ B:BP(I)=B:NEXT 1060 DIM VL(7),VR(7),HL(7),HR(7) 1070 DIM VI(3,7,2,1):REM segment,level,mode,idx-from/idx-to 1080 DIM VK(1392) 1090 RETURN 1100 REM compile-viewport-instr 1110 I4=C0 1120 READ B:IF B<C0 THEN RETURN:REM level 1130 FOR J=C0 TO C2:READ B0:REM mode, get length 1140 JL=B0*C3:I0=I4:I1=I0+JL:I2=I1+JL:I3=I2+JL:I4=I3+JL 1150 VI(C0,B,J,C0)=I0:VI(C0,B,J,C1)=I1-C3 1160 VI(C1,B,J,C0)=I1:VI(C1,B,J,C1)=I2-C3 1170 VI(C2,B,J,C0)=I2:VI(C2,B,J,C1)=I3-C3 1180 VI(C3,B,J,C0)=I3:VI(C3,B,J,C1)=I4-C3 1190 FOR K=C1 TO B0 1193 READ B1,B2,B3:VK(I0)=B1:VK(I1)=B1:VK(I2)=B1:VK(I3)=B1 1196 ON B1 GOTO 1200,1260,1320,1380 1200 VK(I0+C1)=(B2*CP) OR B3 1210 VK(I1+C1)=((C3-B2)*CP) OR B3 1220 VK(I2+C1)=((C3-B2)*CP) OR (CN-B3) 1230 VK(I3+C1)=(B2*CP) OR (CN-B3) 1240 P=B3 1250 GOTO 1430 1260 L=B2-P:P=B2+C1 1270 VK(I0+C1)=L:VK(I0+C2)=BP(B3) 1280 VK(I1+C1)=L:VK(I1+C2)=BP(B3+E8) 1290 VK(I2+C1)=L:VK(I2+C2)=BP(B3+E8) 1300 VK(I3+C1)=L:VK(I3+C2)=BP(B3) 1310 GOTO 1430 1320 L=B2-P+B3:P=B2+C1 1330 VK(I0+C1)=B3:VK(I0+C2)=L 1340 VK(I1+C1)=B3+CE:VK(I1+C2)=L+CE 1350 VK(I2+C1)=B3+CE:VK(I2+C2)=L+CE 1360 VK(I3+C1)=B3:VK(I3+C2)=L 1370 GOTO 1430 1380 VK(I0+C1)=BP(B2):VK(I0+C2)=BP(B3) 1390 VK(I1+C1)=BP(B2+E8):VK(I1+C2)=BP(B3+E8) 1400 VK(I2+C1)=BP(B2+E8):VK(I2+C2)=BP(B3+E8) 1410 VK(I3+C1)=BP(B2):VK(I3+C2)=BP(B3) 1420 P=P+C1 1430 I0=I0+C3:I1=I1+C3:I2=I2+C3:I3=I3+C3 1440 NEXT:NEXT:GOTO 1120 1500 REM assemble view path data 1510 Y=MY:X=MX:VL=DD(DL):VR=DD(DR):VF=DD(MD):W0=CM:FW=C0 1520 FOR I=C0 TO C7:B=M(Y,X) 1523 IF B AND VL THEN VL(I)=C1 ELSE VL(I)=C0 1526 IF B AND VR THEN VR(I)=C1 ELSE VR(I)=C0 1530 IF I=C0 THEN 1570 1540 IF VL(I)<>VL(I-C1) THEN VL(I-C1)=VL(I-C1) OR C2 1560 IF VR(I)<>VR(I-C1) THEN VR(I-C1)=VR(I-C1) OR C2 1570 IF B AND VF THEN 1610 1580 IF VL(I)=C0 THEN VL(I)=C2 ELSE IF M(Y+DY(DL),X+DX(DL)) AND VF THEN VL(I)=C4 ELSE VL(I)=C1 1590 IF VR(I)=C0 THEN VR(I)=C2 ELSE IF M(Y+DY(DR),X+DX(DR)) AND VF THEN VR(I)=C4 ELSE VR(I)=C1 1600 W0=I:FW=I+C1:I=C7:GOTO 1620 1610 X=X+DX:Y=Y+DY 1620 NEXT 1630 IF W0=W1 THEN W1=CM 1640 IF (FW) AND (FW<C8) THEN FOR I=FW TO C7:VL(I)=CM:VR(I)=CM:NEXT 1650 RETURN 1700 REM clear/init viewport 1710 ON G GOSUB 910,920,930,930,940 1720 OUT PA,PL OR PR:OUT PB,C0:REM enable blocks 0,1,5,6 at once 1730 FOR Y=C0 TO C3:OUT PC,Y*CP 1740 FOR X=C0 TO CN:OUT PD,C0:NEXT 1750 NEXT 1760 ON G GOSUB 960,970,980,980,990 1770 FOR I=0 TO 7:HL(I)=CM:HR(I)=CM:NEXT:W0=CM:W1=CM 1780 RETURN 2000 REM port patterns for segments (0..9: PA,PB) 2001 DATA 1,0,2,0,4,0,8,0,16,0,32,0,64,0,128,0,0,1,0,2 2002 REM directions (0..3:dx,dy) 2003 DATA 0,-1,-1,0,0,1,1,0 2004 REM turns (L: 0..3, R: 0..3) 2005 DATA 1,2,3,0, 3,0,1,2 2006 REM directional codes (2^0..3) 2007 DATA 1,2,4,8 2008 REM maze maker defs (0..3:Y,X) 2009 DATA 0,1,1,0,1,1,1,2, 0,1,1,0,1,1,2,1, 1,0,1,1,1,2,2,1, 0,1,1,1,1,2,2,1 2010 REM maze marker turn pixel mods (Y,X) 2011 DATA 2,1,1,0, 1,2,2,1, 0,1,1,2, 1,0,0,1 2012 REM maze bit patterns 2013 DATA 1,3,7,14,28,56,112,224,192,128 2019 REM maze data 2020 DATA 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 2021 DATA 0,12,10,14,10,14,10,10,10,14,10,10,14,2,0,8,14,10,10,10,10,14,10,10,10,14,10,10,10,10,6,0 2022 DATA 0,1,0,5,0,5,0,0,0,5,0,0,5,0,0,0,5,0,0,0,0,5,0,0,0,5,0,0,0,0,5,0 2023 DATA 0,0,0,5,0,9,14,10,10,3,0,12,11,14,10,10,11,14,10,6,0,5,0,12,10,11,6,0,12,10,3,0 2024 DATA 0,4,0,5,0,0,5,0,0,0,0,5,0,1,0,0,0,5,0,5,0,5,0,5,0,0,9,10,7,0,0,0 2025 DATA 0,13,10,15,10,10,11,10,10,10,10,7,0,0,0,4,0,5,0,9,10,11,10,11,6,0,0,0,9,6,0,0 2026 DATA 0,5,0,5,0,0,0,0,0,0,0,5,0,12,10,11,10,7,0,0,0,0,0,0,13,10,10,6,0,9,2,0 2027 DATA 0,5,0,9,10,14,10,10,10,6,0,5,0,5,0,0,0,9,10,10,10,6,0,0,5,0,0,13,2,0,0,0 2028 DATA 0,5,0,0,0,5,0,0,0,13,10,7,0,13,10,6,0,0,0,0,0,5,0,12,11,6,0,5,0,0,4,0 2029 DATA 0,9,10,6,0,13,10,6,0,5,0,5,0,5,0,5,0,12,10,6,0,5,0,5,0,5,0,9,14,10,7,0 2030 DATA 0,0,0,5,0,5,0,1,0,5,0,13,10,7,0,5,0,5,0,5,0,5,0,5,0,5,0,0,5,0,5,0 2031 DATA 0,4,0,5,0,5,0,0,0,5,0,5,0,5,0,5,0,5,0,5,0,5,0,5,0,9,14,10,7,0,5,0 2032 DATA 0,5,0,5,0,9,10,10,10,3,0,5,0,1,0,9,10,11,14,11,10,3,0,9,6,0,5,0,1,0,5,0 2033 DATA 0,5,0,5,0,0,0,0,0,0,0,5,0,0,0,0,0,0,5,0,0,0,0,0,5,0,5,0,0,0,5,0 2034 DATA 0,9,10,11,10,10,10,10,10,10,10,11,10,10,10,10,10,10,11,10,10,10,10,10,11,10,11,10,10,10,3,0 2035 DATA 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 3000 REM segment addresses (port A) 3001 DATA 1,32,64,2 3005 REM line pixels 3006 DATA 1, 1, 2, 2, 4, 4, 8, 8, 16, 16 3007 DATA 32, 32, 64, 64, 128, 128, 64, 64, 32, 32 3008 DATA 16, 16, 8, 8, 4, 4, 2, 2, 1, 1 3010 REM pixels for repeats 3011 DATA 0,1,2,4,8,16,32,64,128 3012 DATA 255,254,252,248,240,224,192,128 3013 REM inverse direction (bottom up) 3014 DATA 0,128,64,32,16,8,4,2,1 3015 DATA 255,127,63,31,15,7,3,1 3020 REM viewport commands struct, 1st quadrant, per level and mode 3021 DATA 0:REM level 0 3022 DATA 10 3023 DATA 1,0,0, 3,5,10 3024 DATA 1,1,0, 2,5,0, 2,6,1, 4,9,1 3025 DATA 1,2,7, 4,9,0 3026 DATA 1,3,7, 4,9,0 3027 DATA 9 3028 DATA 1,0,0, 2,5,0 3029 DATA 1,1,0, 2,6,1, 4,9,1 3030 DATA 1,2,7, 4,9,0 3031 DATA 1,3,7, 4,9,0 3032 DATA 6 3033 DATA 1,1,8, 2,49,1 3034 DATA 1,2,8, 2,49,0 3035 DATA 1,3,8, 2,49,0 3036 DATA 1:REM level 1 3037 DATA 7 3038 DATA 1,1,8, 3,15,2, 4,14,6 3039 DATA 1,2,16, 4,9,0 3040 DATA 1,3,16, 4,9,0 3041 DATA 7 3042 DATA 1,1,8, 2,15,6, 4,14,6 3043 DATA 1,2,16, 4,9,0 3044 DATA 1,3,16, 4,9,0 3045 DATA 6 3046 DATA 1,1,17, 2,49,6 3047 DATA 1,2,17, 2,49,0 3048 DATA 1,3,17, 2,49,0 3049 DATA 2:REM level 2 3050 DATA 8 3051 DATA 1,1,17, 3,21,11 3052 DATA 1,2,17, 2,21,0, 3,23,0, 4,10,2 3053 DATA 1,3,24, 4,9,0 3054 DATA 7 3055 DATA 1,1,17, 2,21,0 3056 DATA 1,2,17, 2,23,2, 4,10,2 3057 DATA 1,3,24, 4,9,0 3058 DATA 4 3059 DATA 1,2,25, 2,49,2 3060 DATA 1,3,25, 2,49,0 3061 DATA 3:REM level 3 3062 DATA 5 3063 DATA 1,2,25, 3,30,3, 4,13,5 3064 DATA 1,3,31, 4,9,0 3065 DATA 5 3066 DATA 1,2,25, 2,30,5, 4,13,5 3067 DATA 1,3,31, 4,9,0 3068 DATA 4 3069 DATA 1,2,32, 2,49,5 3070 DATA 1,3,32, 2,49,0 3071 DATA 4:REM level 4 3072 DATA 5 3073 DATA 1,2,32, 3,36,10, 4,8,8 3074 DATA 1,3,37, 4,9,0 3075 DATA 5 3076 DATA 1,2,32, 2,36,8, 4,8,8 3077 DATA 1,3,37, 4,9,0 3078 DATA 4 3079 DATA 1,2,38, 2,49,8 3080 DATA 1,3,38, 2,49,0 3081 DATA 5:REM level 5 3082 DATA 3 3083 DATA 1,3,38, 3,41,0, 4,11,3 3084 DATA 3 3085 DATA 1,3,38, 2,41,3, 4,11,3 3086 DATA 2 3087 DATA 1,3,43, 2,49,3 3089 DATA 6:REM level 6 3090 DATA 3 3091 DATA 1,3,43, 3,45,5, 4,13,5 3092 DATA 3 3093 DATA 1,3,43, 2,45,5, 4,13,5 3094 DATA 2 3095 DATA 1,3,47, 2,49,5 3096 DATA 7:REM level 7 3097 DATA 3 3098 DATA 1,3,47, 3,48,9, 4,14,14 3099 DATA 3 3100 DATA 1,3,47, 2,48,6, 4,14,14 3101 DATA 2 3102 DATA 1,3,49, 2,49,14 3103 DATA -1
And here it is compressed, without spaces — amazingly faster:
10'Maze War Dungeon Roamer (final, compressed), N.Landsteiner 01/2016 20DEFSNGA:DEFINTB-Z:SCREEN0,0:CLS:?"Setting up...":GOTO200 35'== time critical subroutines == 30'viewport draw commands 31OUTPC,VK(K+C1):RETURN 32B=VK(K+C2):FORJ=C0TOVK(K+C1):OUTPD,B:NEXT:RETURN 33FORJ=VK(K+C1)TOVK(K+C2):OUTPD,BL(J):NEXT:RETURN 34IFVETHENOUTPD,VK(K+C1)ELSEOUTPD,VK(K+C2) 35RETURN 36FORJ=C0TOVK(K+C1):OUTPD,C0:NEXT:RETURN 37FORJ=VK(K+C1)TOVK(K+C2):OUTPD,C0:NEXT:RETURN 39'subroutine: render-viewport 40ONGGOSUB910,920,930,930,940 42OUTPB,C0 44OUTPA,PL:OUTPC,PU:OUTPA,PR:OUTPC,PQ 46FORI=C0TOC7 48IFW0=ITHENGOSUB100:I=C7:GOTO76 50IFW1=ITHENGOSUB90 52IFVL(I)=HL(I)THEN64 54VM=VL(I)ANDC1:VE=VL(I)ANDC2 56FORVS=C0TOC1:OUTPA,PV(VS) 58FORK=VI(VS,I,VM,C0)TOVI(VS,I,VM,C1)STEPC3 60ONVK(K)GOSUB31,32,33,34 62NEXT:NEXT 64IFVR(I)=HR(I)THEN76 66VM=VR(I)ANDC1:VE=VR(I)ANDC2 68FORVS=C2TOC3:OUTPA,PV(VS) 70FORK=VI(VS,I,VM,C0)TOVI(VS,I,VM,C1)STEPC3 72ONVK(K)GOSUB31,32,33,34 74NEXT:NEXT 76NEXT 78FORI=C0TOC7:HL(I)=VL(I):HR(I)=VR(I):NEXT:W1=W0 80OUTPA,PR:OUTPC,PU 82ONGGOSUB960,970,980,980,990 84RETURN 89'erase a wall 90IFW1=C7THENRETURN 92FORVS=C0TOC3:OUTPA,PV(VS):K=VI(VS,W1,C2,C0):OUTPC,VK(K+C1) 94FORJ=C0TOVK(K+C4):OUTPD,C0:NEXT 96NEXT:RETURN 98'draw blocking wall; handle left side 100IFVL(W0)=C4THEN112 102VM=VL(W0)ANDC1:VE=VL(W0)ANDC2 104FORVS=C0TOC1:OUTPA,PV(VS) 106FORK=VI(VS,W0,VM,C0)TOVI(VS,W0,VM,C1)STEPC3 108ONVK(K)GOSUB31,32,33,34 110NEXT:NEXT:GOTO124 112VE=C1:'passage to the left and ahead 114FORVS=C0TOC1:OUTPA,PV(VS) 116FORK=VI(VS,W0,C1,C0)TOVI(VS,W0,C1,C1)STEPC3 118ONVK(K)GOSUB31,36,37,34 120NEXT:NEXT 122'handle right side 124IFVR(W0)=C4THEN136 126VM=VR(W0)ANDC1:VE=VL(W0)ANDC2 128FORVS=C2TOC3:OUTPA,PV(VS) 130FORK=VI(VS,W0,VM,C0)TOVI(VS,W0,VM,C1)STEPC3 132ONVK(K)GOSUB31,32,33,34 134NEXT:NEXT:GOTO148 136VE=C1:'passage to the right and ahead 138FORVS=C2TOC3:OUTPA,PV(VS) 140FORK=VI(VS,W0,C1,C0)TOVI(VS,W0,C1,C1)STEPC3 142ONVK(K)GOSUB31,36,37,34 144NEXT:NEXT 146'finally draw the wall 148IFW0=C7THENRETURN 150FORVS=C0TOC3:OUTPA,PV(VS) 152FORK=VI(VS,W0,C2,C0)TOVI(VS,W0,C2,C1)STEPC3 154ONVK(K)GOSUB31,32,33,34 156NEXT:NEXT 158RETURN 160'== setup, execution starts here == 195'G: 1=PC-8201A, 2=M10 (w/o modem), 3=Model 100, 4=Model 102, 5=KC85 200B=PEEK(1):G=-(B=148)-(B=35)*2-(B=51)*3-(B=167)*4-(B=225)*5 205IFG=0THENSCREEN0,1:?"Sorry, model not supported. Gestalt:";B:END 210IFG=1THENAK=65128!ELSEIFG=2THENAK=65389!ELSEIFG=5THENAK=65387!ELSEAK=65450! 215C0=0:C1=1:C2=2:C3=3:C4=4:C5=5:C6=6:C7=7:C8=8:C9=9 220CA=10:CC=12:CE=14:CN=49:CL=50:CP=64:CM=-1 225UC=223:LC=97:CK=27:ES=27:EB=32:E8=17 230PA=185:PB=186:PC=254:PD=255:DIMSA(9),SB(9):SG=-1:SH=0 235FORI=C0TOC9:READB1,B2:SA(I)=B1:SB(I)=B2:NEXT 240DX=0:DY=0:DIMDX(3),DY(3):FORI=C0TOC3:READB1,B2:DX(I)=B1:DY(I)=B2:NEXT 245DL=0:DR=0:DIMDL(3),DR(3) 250FORI=C0TOC3:READB:DL(I)=B:NEXT 255FORI=C0TOC3:READB:DR(I)=B:NEXT 260DIMDD(3):FORI=C0TOC3:READB:DD(I)=B:NEXT 269'setup the maze 270DIMSM(3,3,2):FORI=C0TOC3:FORY=C0TOC3:READB1,B2:SM(I,Y,C1)=B1:SM(I,Y,C0)=B2:NEXT:NEXT 275DIMST(3,1,1):FORI=C0TOC3:FORY=C0TOC1:READB1,B2:ST(I,Y,C1)=B1:ST(I,Y,C0)=B2:NEXT:NEXT 280MW=31:MH=15:ML=132:MT=5:DIMM(MH,MW),BM(C9) 285FORY=C0TOC9:READB:BM(Y)=B:NEXT 290FORY=C0TOMH:FORX=C0TOMW:READB:M(Y,X)=B:NEXT:NEXT 295GOSUB1010:GOSUB1110:'setup viewport 299'== main == 300CLS:GOSUB700:MX=11:MY=7:MD=0:DX=DX(MD):DY=DY(MD):DL=DL(MD):DR=DR(MD) 310?CHR$(ES);"Y";CHR$(EB+C7);CHR$(EB+22);"Crsr,IJKL,Q:quit"; 315GOSUB460:GOSUB1770:GOSUB1510:GOSUB40 319'main loop 320B=PEEK(AK):IFB=C0THEN320 330K=PEEK(AK+B):POKEAK,C0:IFK>CKTHENONK-CKGOTO500,520,540,560 340IFK>=LCTHENK=KANDUC 350ONINSTR("JLKI Q",CHR$(K))GOTO520,500,560,540,580,590 360GOTO320 398'== subroutines == 399'segement/pos select 400SH=SG:SG=SX\CL:IFSY>C3THENSG=SG+C5 410IF(SG<>SH)THENOUTPA,SA(SG):OUTPB,SB(SG) 420OUTPC,(SYMODC4)*CPORSXMODCL:RETURN 449'clear/draw marker 450X=ML+MX*C3:Y=MT+MY*C3:FORI=C0TOC3:PRESET(X+SM(MD,I,C0),Y+SM(MD,I,C1)):NEXT:RETURN 460X=ML+MX*C3:Y=MT+MY*C3:FORI=C0TOC3:PSET(X+SM(MD,I,C0),Y+SM(MD,I,C1)):NEXT:RETURN 470X=ML+MX*C3:Y=MT+MY*C3:PRESET(X+ST(MD,T0,C0),Y+ST(MD,T0,C1)):PSET(X+ST(MD,T1,C0),Y+ST(MD,T1,C1)):RETURN 499'key handling (right, left, bkwd, fwd, fire, quit) 500T0=C1:T1=C0:GOSUB470:MD=DR:DX=DX(MD):DY=DY(MD):DL=DL(MD):DR=DR(MD):GOTO610 520MD=DL:T0=C0:T1=C1:GOSUB470:DX=DX(MD):DY=DY(MD):DL=DL(MD):DR=DR(MD):GOTO610 540GOSUB450:MX=MX+DX:MY=MY+DY:IFM(MY,MX)=C0THENMX=MX-DX:MY=MY-DY:GOSUB460:GOTO320 550GOSUB460:GOTO610 560GOSUB450:MX=MX-DX:MY=MY-DY:IFM(MY,MX)=C0THENMX=MX+DX:MY=MY+DY:GOSUB460:GOTO320 570GOSUB460:GOTO610 580GOTO320:'shoot 590SCREEN0,1:CLS:?"- Bye -":END 600'view port: get path and display it 610GOSUB1510:GOSUB40:GOTO320 699'maze display 700SY=MT\C8:Y0=0:D=MTMODC8+C2:ONGGOSUB910,920,930,930,940 710Y1=Y0+C1:Y2=Y0+C2:Y3=Y0+C3:B0=BM(D) 720IF(Y1<=MH)AND(D<C7)THENB1=BM(D+C3)ELSEB1=C0 730IF(Y2<=MH)AND(D<C4)THENB2=BM(D+C6)ELSEB2=C0 740IF(Y3<=MH)AND(D=C0)THENB3=BM(D+C9)ELSEB3=C0 750SX=ML:GOSUB400 760FORMX=C0TOMW:IFM(Y0,MX)=C0THENB=B0ELSEB=C0 770IFB1THENIFM(Y1,MX)=C0THENB=BORB1 780IFB2THENIFM(Y2,MX)=C0THENB=BORB2 790IFB3THENIFM(Y3,MX)=C0THENB=BORB3 800FORI=C0TOC2:IFSXMODCL=C0THENGOSUB400 810OUTPD,B:SX=SX+C1:NEXT:NEXT 820Y0=Y0+(CA-D)\C3:IFY0>MHTHEN840 830D=(D+C1)MODC3:SY=SY+C1:GOTO710 840ONGGOSUB960,970,980,980,990:RETURN 900'disable interrupts 910EXEC30437:RETURN 920CALL29558:RETURN 930CALL30300:RETURN 940CALL29450:RETURN 950'enable interrupts 960EXEC29888:RETURN 970CALL28998:RETURN 980CALL29756:RETURN 990CALL28906:RETURN 1000'setup viewport 1010PL=33:PR=66:'LCD blocks 0+5, 1+6 1020PU=59:PQ=58:'LCD counter setting increment/decrement 1030DIMPV(3):FORI=0TO3:READB:PV(I)=B:NEXT 1040DIMBL(29):FORI=0TO29:READB:BL(I)=B:NEXT 1050DIMBP(33):FORI=0TO33:READB:BP(I)=B:NEXT 1060DIMVL(7),VR(7),HL(7),HR(7) 1070DIMVI(3,7,2,1):'segment,level,mode,idx-from/idx-to 1080DIMVK(1392) 1090RETURN 1100'compile-viewport-instr 1110I4=C0 1120READB:IFB<C0THENRETURN:'level 1130FORJ=C0TOC2:READB0:'mode, get length 1140JL=B0*C3:I0=I4:I1=I0+JL:I2=I1+JL:I3=I2+JL:I4=I3+JL 1150VI(C0,B,J,C0)=I0:VI(C0,B,J,C1)=I1-C3 1160VI(C1,B,J,C0)=I1:VI(C1,B,J,C1)=I2-C3 1170VI(C2,B,J,C0)=I2:VI(C2,B,J,C1)=I3-C3 1180VI(C3,B,J,C0)=I3:VI(C3,B,J,C1)=I4-C3 1190FORK=C1TOB0 1193READB1,B2,B3:VK(I0)=B1:VK(I1)=B1:VK(I2)=B1:VK(I3)=B1 1196ONB1GOTO1200,1260,1320,1380 1200VK(I0+C1)=(B2*CP)ORB3 1210VK(I1+C1)=((C3-B2)*CP)ORB3 1220VK(I2+C1)=((C3-B2)*CP)OR(CN-B3) 1230VK(I3+C1)=(B2*CP)OR(CN-B3) 1240P=B3 1250GOTO1430 1260L=B2-P:P=B2+C1 1270VK(I0+C1)=L:VK(I0+C2)=BP(B3) 1280VK(I1+C1)=L:VK(I1+C2)=BP(B3+E8) 1290VK(I2+C1)=L:VK(I2+C2)=BP(B3+E8) 1300VK(I3+C1)=L:VK(I3+C2)=BP(B3) 1310GOTO1430 1320L=B2-P+B3:P=B2+C1 1330VK(I0+C1)=B3:VK(I0+C2)=L 1340VK(I1+C1)=B3+CE:VK(I1+C2)=L+CE 1350VK(I2+C1)=B3+CE:VK(I2+C2)=L+CE 1360VK(I3+C1)=B3:VK(I3+C2)=L 1370GOTO1430 1380VK(I0+C1)=BP(B2):VK(I0+C2)=BP(B3) 1390VK(I1+C1)=BP(B2+E8):VK(I1+C2)=BP(B3+E8) 1400VK(I2+C1)=BP(B2+E8):VK(I2+C2)=BP(B3+E8) 1410VK(I3+C1)=BP(B2):VK(I3+C2)=BP(B3) 1420P=P+C1 1430I0=I0+C3:I1=I1+C3:I2=I2+C3:I3=I3+C3 1440NEXT:NEXT:GOTO1120 1500'assemble view path data 1510Y=MY:X=MX:VL=DD(DL):VR=DD(DR):VF=DD(MD):W0=CM:FW=C0 1520FORI=C0TOC7:B=M(Y,X) 1523IFBANDVLTHENVL(I)=C1ELSEVL(I)=C0 1526IFBANDVRTHENVR(I)=C1ELSEVR(I)=C0 1530IFI=C0THEN1570 1540IFVL(I)<>VL(I-C1)THENVL(I-C1)=VL(I-C1)ORC2 1560IFVR(I)<>VR(I-C1)THENVR(I-C1)=VR(I-C1)ORC2 1570IFBANDVFTHEN1610 1580IFVL(I)=C0THENVL(I)=C2ELSEIFM(Y+DY(DL),X+DX(DL))ANDVFTHENVL(I)=C4ELSEVL(I)=C1 1590IFVR(I)=C0THENVR(I)=C2ELSEIFM(Y+DY(DR),X+DX(DR))ANDVFTHENVR(I)=C4ELSEVR(I)=C1 1600W0=I:FW=I+C1:I=C7:GOTO1620 1610X=X+DX:Y=Y+DY 1620NEXT 1630IFW0=W1THENW1=CM 1640IF(FW)AND(FW<C8)THENFORI=FWTOC7:VL(I)=CM:VR(I)=CM:NEXT 1650RETURN 1700'clear/init viewport 1710ONGGOSUB910,920,930,930,940 1720OUTPA,PLORPR:OUTPB,C0:'enable blocks 0,1,5,6 at once 1730FORY=C0TOC3:OUTPC,Y*CP 1740FORX=C0TOCN:OUTPD,C0:NEXT 1750NEXT 1760ONGGOSUB960,970,980,980,990 1770FORI=0TO7:HL(I)=CM:HR(I)=CM:NEXT:W0=CM:W1=CM 1780RETURN 2000'port patterns for segments (0..9: PA,PB) 2001DATA1,0,2,0,4,0,8,0,16,0,32,0,64,0,128,0,0,1,0,2 2002'directions (0..3:dx,dy) 2003DATA0,-1,-1,0,0,1,1,0 2004'turns (L: 0..3, R: 0..3) 2005DATA1,2,3,0,3,0,1,2 2006'directional codes (2^0..3) 2007DATA1,2,4,8 2008'maze maker defs (0..3:Y,X) 2009DATA0,1,1,0,1,1,1,2,0,1,1,0,1,1,2,1,1,0,1,1,1,2,2,1,0,1,1,1,1,2,2,1 2010'maze marker turn pixel mods (Y,X) 2011DATA2,1,1,0,1,2,2,1,0,1,1,2,1,0,0,1 2012'maze bit patterns 2013DATA1,3,7,14,28,56,112,224,192,128 2019'maze data 2020DATA0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 2021DATA0,12,10,14,10,14,10,10,10,14,10,10,14,2,0,8,14,10,10,10,10,14,10,10,10,14,10,10,10,10,6,0 2022DATA0,1,0,5,0,5,0,0,0,5,0,0,5,0,0,0,5,0,0,0,0,5,0,0,0,5,0,0,0,0,5,0 2023DATA0,0,0,5,0,9,14,10,10,3,0,12,11,14,10,10,11,14,10,6,0,5,0,12,10,11,6,0,12,10,3,0 2024DATA0,4,0,5,0,0,5,0,0,0,0,5,0,1,0,0,0,5,0,5,0,5,0,5,0,0,9,10,7,0,0,0 2025DATA0,13,10,15,10,10,11,10,10,10,10,7,0,0,0,4,0,5,0,9,10,11,10,11,6,0,0,0,9,6,0,0 2026DATA0,5,0,5,0,0,0,0,0,0,0,5,0,12,10,11,10,7,0,0,0,0,0,0,13,10,10,6,0,9,2,0 2027DATA0,5,0,9,10,14,10,10,10,6,0,5,0,5,0,0,0,9,10,10,10,6,0,0,5,0,0,13,2,0,0,0 2028DATA0,5,0,0,0,5,0,0,0,13,10,7,0,13,10,6,0,0,0,0,0,5,0,12,11,6,0,5,0,0,4,0 2029DATA0,9,10,6,0,13,10,6,0,5,0,5,0,5,0,5,0,12,10,6,0,5,0,5,0,5,0,9,14,10,7,0 2030DATA0,0,0,5,0,5,0,1,0,5,0,13,10,7,0,5,0,5,0,5,0,5,0,5,0,5,0,0,5,0,5,0 2031DATA0,4,0,5,0,5,0,0,0,5,0,5,0,5,0,5,0,5,0,5,0,5,0,5,0,9,14,10,7,0,5,0 2032DATA0,5,0,5,0,9,10,10,10,3,0,5,0,1,0,9,10,11,14,11,10,3,0,9,6,0,5,0,1,0,5,0 2033DATA0,5,0,5,0,0,0,0,0,0,0,5,0,0,0,0,0,0,5,0,0,0,0,0,5,0,5,0,0,0,5,0 2034DATA0,9,10,11,10,10,10,10,10,10,10,11,10,10,10,10,10,10,11,10,10,10,10,10,11,10,11,10,10,10,3,0 2035DATA0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 3000'segment addresses (port A) 3001DATA1,32,64,2 3005'line pixels 3006DATA1,1,2,2,4,4,8,8,16,16 3007DATA32,32,64,64,128,128,64,64,32,32 3008DATA16,16,8,8,4,4,2,2,1,1 3010'pixels for repeats 3011DATA0,1,2,4,8,16,32,64,128 3012DATA255,254,252,248,240,224,192,128 3013'inverse direction (bottom up) 3014DATA0,128,64,32,16,8,4,2,1 3015DATA255,127,63,31,15,7,3,1 3020'viewport commands struct, 1st quadrant, per level and mode 3021DATA0:'level 0 3022DATA10 3023DATA1,0,0,3,5,10 3024DATA1,1,0,2,5,0,2,6,1,4,9,1 3025DATA1,2,7,4,9,0 3026DATA1,3,7,4,9,0 3027DATA9 3028DATA1,0,0,2,5,0 3029DATA1,1,0,2,6,1,4,9,1 3030DATA1,2,7,4,9,0 3031DATA1,3,7,4,9,0 3032DATA6 3033DATA1,1,8,2,49,1 3034DATA1,2,8,2,49,0 3035DATA1,3,8,2,49,0 3036DATA1:'level 1 3037DATA7 3038DATA1,1,8,3,15,2,4,14,6 3039DATA1,2,16,4,9,0 3040DATA1,3,16,4,9,0 3041DATA7 3042DATA1,1,8,2,15,6,4,14,6 3043DATA1,2,16,4,9,0 3044DATA1,3,16,4,9,0 3045DATA6 3046DATA1,1,17,2,49,6 3047DATA1,2,17,2,49,0 3048DATA1,3,17,2,49,0 3049DATA2:'level 2 3050DATA8 3051DATA1,1,17,3,21,11 3052DATA1,2,17,2,21,0,3,23,0,4,10,2 3053DATA1,3,24,4,9,0 3054DATA7 3055DATA1,1,17,2,21,0 3056DATA1,2,17,2,23,2,4,10,2 3057DATA1,3,24,4,9,0 3058DATA4 3059DATA1,2,25,2,49,2 3060DATA1,3,25,2,49,0 3061DATA3:'level 3 3062DATA5 3063DATA1,2,25,3,30,3,4,13,5 3064DATA1,3,31,4,9,0 3065DATA5 3066DATA1,2,25,2,30,5,4,13,5 3067DATA1,3,31,4,9,0 3068DATA4 3069DATA1,2,32,2,49,5 3070DATA1,3,32,2,49,0 3071DATA4:'level 4 3072DATA5 3073DATA1,2,32,3,36,10,4,8,8 3074DATA1,3,37,4,9,0 3075DATA5 3076DATA1,2,32,2,36,8,4,8,8 3077DATA1,3,37,4,9,0 3078DATA4 3079DATA1,2,38,2,49,8 3080DATA1,3,38,2,49,0 3081DATA5:'level 5 3082DATA3 3083DATA1,3,38,3,41,0,4,11,3 3084DATA3 3085DATA1,3,38,2,41,3,4,11,3 3086DATA2 3087DATA1,3,43,2,49,3 3089DATA6:'level 6 3090DATA3 3091DATA1,3,43,3,45,5,4,13,5 3092DATA3 3093DATA1,3,43,2,45,5,4,13,5 3094DATA2 3095DATA1,3,47,2,49,5 3096DATA7:'level 7 3097DATA3 3098DATA1,3,47,3,48,9,4,14,14 3099DATA3 3100DATA1,3,47,2,48,6,4,14,14 3101DATA2 3102DATA1,3,49,2,49,14 3103DATA-1
The compressed program (diff.: 1,335 bytes) executes faster by a remarkable amount and is suitably responsive for an interactive game! — Finally, we met our goal of doing some usable pseudo-3D in BASIC only. Not a bad ending, at all!
Download it here: ▶ MazeWarRoamer.txt
Before we close, a last glance at our trusty Olivetti M10 running the program:
And here, we arrived at the end of our story, even at the end of the addendum to it. I guess, we'll have to find out, if there is such a thing as an addendum to the addendum. I might be in error, but I do not think so …
Cheers, again, and thanks again to all who followed these posts, and, finally,
— finis —
◀ Previous: Episode 12: A Screen With A View
▲ Back to the index.
2016-02-02, Vienna, Austria
www.masswerk.at – contact me.
— This series is part of Retrochallenge 2016/01. —