jonah: ambidirectional scrolling, 9 levels
[wormy.git] / worm.asm
1 ; -WonderWorm--v0.9-
2 ; by Matthew Shepcar
3 ; 30th December 1998
4
5 ; modified by Jonah Cohen 11-14-99
6
7 #include "TI86.inc"
8
9 .org _asm_exec_ram
10
11   nop
12   jp Start
13   .dw 0,WormMsg
14 Start:
15   ld (SpSave),sp
16   call _runIndicOff
17   call _clrLCD
18
19   call BuildTrigTables
20
21   ld a,r
22   ld (Seed),a
23
24   ld hl,0
25   ld (Score),hl
26   ld a,1
27   ld (Level),a
28   ld a,3
29   ld (Lives),a
30   ld hl,Levels
31
32 StartLevel:
33   ld a,(hl)
34   ld (Left),a
35   inc hl
36   ld a,(hl)
37   ld (Speed),a
38   inc hl
39   ld a,25
40 NextLife:
41   ld (GrowAmt),a
42   push hl
43   ld d,(hl)
44   inc hl
45   ld e,(hl)
46   inc hl
47   ld a,(hl)
48   inc hl
49   ld (Heading),a
50   push de
51   ld a,(hl)
52   inc hl
53   sub 57
54   ld (FieldHeight),a
55   add a,57-5
56   push hl
57   ld l,a
58   ld h,0
59   add hl,hl
60   add hl,hl
61   add hl,hl
62   add hl,hl
63   ex de,hl
64
65   ld hl,ScrBuffer
66   push hl
67   push de
68   ld de,ScrBuffer+1
69   ld bc,31
70   ld (hl),-1
71   ldir
72   inc hl
73   ld (hl),192
74   inc hl
75   ld b,14
76 ClearLine:
77   ld (hl),c
78   inc hl
79   djnz ClearLine
80   ld (hl),3
81   inc hl
82   ex de,hl
83   pop bc
84   ldir
85   pop hl
86   ld c,32
87   ldir
88   pop hl
89
90   ld a,(hl)
91   inc hl
92   or a
93   jr z,NoLines
94 DrawLines:
95   push af
96   ld d,(hl)
97   inc hl
98   ld e,(hl)
99   inc hl
100   ld a,(hl)
101   inc hl
102   push hl
103   ld l,(hl)
104   ld h,a
105   call Line
106   inc d
107   inc h
108   call Line
109   inc e
110   inc l
111   call Line
112   dec d
113   dec h
114   call Line
115   pop hl
116   inc hl
117   pop af
118   dec a
119   jr nz,DrawLines
120 NoLines:
121   push hl
122
123   ld hl,0
124   ld (_penCol),hl
125   ld hl,LivesMsg
126   call _vputs
127   ld a,(Lives)
128   add a,'0'
129   call _vputmap
130
131   ld a,40
132   ld (_penCol),a
133   call _vputs ;scoremsg
134   ld a,100
135   ld (_penCol),a
136   call _vputs
137   ld a,(Left)
138   call PutNum
139
140   call PutScore
141
142   call NewPea
143
144   xor a
145   call DisplayField
146   ld hl,LevelMsg
147   ld a,7
148   call DispMsg
149   ld a,(Level)
150   add a,'0'
151   call _putc
152   res 3,(iy+5)
153
154   xor a
155 ReadyDelay:
156   halt
157   dec a
158   jr nz,ReadyDelay
159
160   ld hl,(HeadPos)
161   ld (TailPos),hl
162   pop hl
163   pop bc
164   push hl
165   ld de,0
166
167 GameLoop:
168   ld a,c
169   sub 29
170   jr nc,NotMinScroll
171   xor a
172 NotMinScroll:
173   cp 43
174 FieldHeight =$-1
175   jr c,NotMaxScroll
176   ld a,(FieldHeight)
177 NotMaxScroll:
178   call DisplayField
179
180   ld a,9
181 Speed =$-1
182 Delay:
183   halt
184   dec a
185   jr nz,Delay
186
187   ld hl,0A000h
188 HeadPos =$-2
189   ld (hl),c
190   inc hl
191   ld (hl),b
192   inc hl
193   res 4,h
194   ld (HeadPos),hl
195
196   ld hl,SinCosTable
197 Heading =$-2
198
199   ld a,0FEh
200   out (1),a
201   in a,(1)
202   rra
203   rra
204   jr c,NotRight
205   push af
206   ld a,l
207   add a,8
208   ld l,a
209   pop af
210 NotRight:
211   rra
212   jr c,NotLeft
213   ld a,l
214   sub 8
215   ld l,a
216 NotLeft:
217
218   ld (Heading),hl
219
220   push bc
221   ld a,(hl)
222   add a,a
223   add a,d
224   ld d,a
225   bit 7,(hl)
226   jr z,NotNegX
227   dec b
228 NotNegX:
229   jr nc,NotMoveX
230   inc b
231 NotMoveX:
232   ld a,l
233   add a,40h
234   ld l,a
235   ld a,(hl)
236   add a,a
237   add a,e
238   ld e,a
239   bit 7,(hl)
240   jr z,NotNegY
241   dec c
242 NotNegY:
243   jr nc,NotMoveY
244   inc c
245 NotMoveY:
246
247   pop hl
248   push de
249   ld a,h
250   sub b
251   and 1
252   ld h,a
253   ld a,l
254   sub c
255   and 1
256   add a,h
257   ld d,4
258   jr z,GotFour
259   xor 3
260   ld d,a
261 GotFour:
262
263   call CheckPixel
264   inc b
265   call CheckPixel
266   inc c
267   call CheckPixel
268   dec b
269   call CheckPixel
270   dec c
271   rl d
272   jr nc,WormNotCrashed
273   ld hl,0
274 PeaY =$-2
275 PeaX =$-1
276   ld a,b
277   sub h
278   inc a
279   cp 4
280   jp nc,WormDead
281   ld a,c
282   sub l
283   inc a
284   cp 4
285   jp nc,WormDead
286   push bc
287   call DrawPea
288   ld a,0
289 GrowAmt =$-1
290   add a,15
291   ld (GrowAmt),a
292   call NewPea
293   ld de,10
294   call IncScore
295   ld a,119
296   ld (_penCol),a
297   ld hl,Left
298   dec (hl)
299   jr nz,NotNextLevel
300   ld hl,Level
301   ld a,(hl)
302   inc (hl)
303   pop bc
304   pop de
305   pop hl
306   pop de
307   cp NUM_LEVELS
308   jp nz,StartLevel
309   jr Exit
310
311 NotNextLevel:
312   ld a,(hl)
313   call PutNum
314   pop bc
315 WormNotCrashed:
316
317   push bc
318   ld a,3
319 WormCol =$-1
320   call SetPixel
321   inc b
322   call SetPixel
323   inc c
324   call SetPixel
325   dec b
326   call SetPixel
327
328 ;  xor 2
329 ;  ld (WormCol),a
330
331   ld hl,GrowAmt
332   dec (hl)
333   jr nz,GrowWorm
334   inc (hl)
335   ld hl,0A000h
336 TailPos =$-2
337   ld c,(hl)
338   inc hl
339   ld b,(hl)
340   inc hl
341   res 4,h
342   ld (TailPos),hl
343
344   call ResPixel
345   inc b
346   call ResPixel
347   inc c
348   call ResPixel
349   dec b
350   call ResPixel
351
352 GrowWorm:
353
354   ld a,0BFh
355   out (1),a
356   in a,(1)
357   rla
358   jr c,NotPaused
359   ld bc,$0103
360   out (c),b
361   halt
362   ld b,11
363   out (c),b
364 NotPaused:
365   pop bc
366   pop de
367   rla
368   jp c,GameLoop
369   jr Exit
370 ; push hl
371 WormDead:
372   pop de
373   pop hl
374   ld hl,(HeadPos)
375   ld de,(TailPos)
376   sbc hl,de
377   ld a,l
378   rr h
379   rra
380   ld hl,Lives
381   dec (hl)
382   pop hl
383   jp nz,NextLife
384 Exit:
385
386 #if 0
387   ld a,(Eaten)
388   ld hl,HiScore
389   cp (hl)
390   jr c,NotNewHigh
391   ld (hl),a
392   ld hl,_asapvar
393   rst 20h
394   rst 10h
395   call 460Bh
396   ld de,HiScore-_asm_exec_ram+2
397   add hl,de
398   adc a,0
399   call _load_ram_ahl
400   ld a,(HiScore)
401   ld (hl),a
402 NotNewHigh:
403 #endif
404   ld sp,0
405 SpSave = $-2
406   jp _clrWindow
407
408 NewPea: ;------------------------------procs
409   call Random
410   ld a,h
411   and 7Fh
412   cp 77h
413   jr nc,NewPea
414   add a,3
415   ld h,a
416   ld a,(FieldHeight)
417   add a,57-12
418   ld b,a
419   ld a,l
420   and 7Fh
421   cp b
422   jr nc,NewPea
423   add a,5
424   ld l,a
425   ld (PeaY),hl
426   ld d,2
427   push hl
428   call CheckPea
429   pop hl
430   dec d
431   jr z,NewPea
432 DrawPea:
433   ld d,0
434 CheckPea:
435   ld b,h
436   ld c,l
437   call PeaPixel
438   inc c
439   call PeaPixel
440   inc b
441   call PeaPixel
442   dec c
443 PeaPixel:
444   push de
445   call FindPixel
446   pop de
447   ld e,a
448   ld a,d
449   or a
450   ld a,e
451   jr z,DrawPeaPixel
452   and (hl)
453   ret z
454   ld d,1
455   ret
456 DrawPeaPixel:
457   xor (hl)
458   ld (hl),a
459   ret
460
461 Random:
462   ld hl,0
463   ld de,12345
464 Seed =$-2
465   ld a,7921 & 255
466   ld bc,1000h+(7921/256)
467 domult16:
468   add hl,hl
469   rla
470   rl c
471   jr nc,noadd16
472   add hl,de
473 noadd16:
474   djnz domult16
475   inc hl
476   ld (Seed),hl ;seed=(seed*7921+1) MOD 65536
477   ld a,h
478   ret
479
480 ResPixel: ;at bc
481   call FindPixel
482   cpl
483   and (hl)
484   ld  (hl),a
485   ret
486
487 SetPixel: ;at bc
488   call FindPixel
489   or  (hl)
490   ld  (hl),a
491   ret
492
493 CheckPixel: ;at bc in d
494   push de
495   call FindPixel
496   and (hl)
497   pop de
498   ret z
499   dec d
500   ret
501
502 FindPixel: ;bc to ahl + de gone
503   push bc
504   ld a,b
505   and 7
506   add a,offsets_table & 255
507   ld e,a
508   ld d,offsets_table/256
509   ld h,0
510   ld a,c
511   add a,a
512   add a,a
513   rl h
514   add a,a
515   rl h
516   add a,a
517   rl h
518   srl b
519   srl b
520   srl b
521   or b
522   ld l,a
523   ld a,(de)
524   ld de,ScrBuffer
525   add hl,de
526   pop bc
527   ret
528
529 IncScore:
530   ld hl,(Score)
531   add hl,de
532   ld (Score),hl
533 PutScore:
534   ld hl,-1
535   ld (_curRow),hl
536   ld a,63
537   ld (_penCol),a
538   ld hl,(Score)
539   xor a
540   call 4A33h
541   dec hl
542   ld b,5
543 DoPutScore:
544   ld a,(hl)
545   inc hl
546   cp 32
547   jr nz,NotZeroDigit
548   ld a,'0'
549 NotZeroDigit:
550   call _vputmap
551   djnz DoPutScore
552   ret
553
554 PutNum:
555   ld l,a
556   ld h,0
557   call _divHLby10
558   push af
559   ld a,l
560   call PutDigit
561   pop af
562 PutDigit:
563   add a,'0'
564   jp _vputmap
565
566 offsets_table:
567   .db 128,64,32,16,8,4,2,1
568
569 DisplayField:
570   ld  l,a
571   ld  h,0
572   add hl,hl
573   add hl,hl
574   add hl,hl
575   add hl,hl
576   push bc
577   push de
578   ld  de,ScrBuffer
579   add hl,de
580   ld  de,$FC00+$70
581   ld  bc,$0390
582   ldir
583   pop de
584   pop bc
585   ret
586
587 DispMsg:
588   push hl
589   ld h,a
590   ld l,4
591   ld (_curRow),hl
592   ld hl,0FDE0h
593   ld de,0FDE1h
594   ld (hl),-1
595   ld bc,0BFh
596   ldir
597   pop hl
598   set 3,(iy+5)
599   jp _puts
600
601
602 NUM_LEVELS = 9
603
604 Levels:
605   .db 5,9           ;5 peas, speed 7
606   .db 64,4,0        ;x,y,d
607   .db 57            ;field height
608   .db 0             ;no additional lines
609
610   .db 8,9
611   .db 4,14,$40
612   .db 57
613   .db 1
614   .db 28,28,100,28
615
616   .db 9,8
617   .db 4,8,$40
618   .db 57
619   .db 2
620   .db 28,14,100,14
621   .db 28,41,100,41
622
623   .db 9,8
624   .db 4,8,$40
625   .db 80
626   .db 2
627   .db 64,14,64,66
628   .db 20,40,108,40
629
630   .db 10,7
631   .db 4,8,$40
632   .db 90
633   .db 3
634   .db 18,20,18,70
635   .db 110,20,110,70
636   .db 18,45,110,45
637
638   .db 7,7
639   .db 64,4,0
640   .db 86
641   .db 6
642   .db 34,13,56,35
643   .db 34,71,56,49
644   .db 72,35,94,13
645   .db 72,49,94,71
646   .db 16,20,16,64
647   .db 110,20,110,64
648
649   .db 9,7
650   .db 4,10,$40
651   .db 82
652   .db 3
653   .db 0,20,74,20
654   .db 54,40,128,40
655   .db 0,60,74,60
656
657   .db 12,7
658   .db 64,4,0
659   .db 90
660   .db 6
661   .db 20,16,54,16
662   .db 74,16,110,16
663   .db 20,16,20,72
664   .db 110,16,110,72
665   .db 20,72,54,72
666   .db 74,72,110,72
667
668   .db 8,7
669   .db 72,52,$c0
670   .db 128
671   .db 13
672   .db 34,56,56,34
673   .db 34,72,56,94
674   .db 72,34,94,56
675   .db 72,94,94,72
676   .db 46,64,80,64
677   .db 22,11,22,33
678   .db 11,22,33,22
679   .db 22,95,22,117
680   .db 11,106,33,106
681   .db 103,11,103,33
682   .db 91,22,115,22
683   .db 103,95,103,117
684   .db 91,106,115,106
685
686
687
688 #include "trigtab.asm"
689 #include "line.asm"
690
691 WormMsg .db "Wonderworm!",0
692 LevelMsg .db "Level ",0
693 LivesMsg .db "Lives: ",0
694 ScoreMsg .db "Score: ",0
695 LeftMsg  .db "Food: ",0
696 HiScore .db 0
697
698 Left =$
699 Lives =$+1
700 Level =$+2
701 Score =$+3
702
703 SinCosTable =09E00h
704 ScrBuffer =8200h ;size $1400 (at least)
705
706 .end
707 eft:
708   dec hl
709   rl (hl)
710   djnz ShiftRowLeft
711   pop hl
712   dec c
713   jr nz,ShiftRowsLeft
714   ld bc,-16
715   add hl,bc
716   ex de,hl
717   pop bc
718   djnz ShiftLeftLoop
719   ld a,(ShiftBitsLeft)
720   jr NoShift
721 ShiftRight:
722   dec hl
723   ex de,hl
724   ld c,16
725   sbc hl,bc
726   ex de,hl
727   ld b,57
728   cpl
729   add a,9
730   ld (ShiftBitsRight),a
731 ShiftRightLoop:
732   push bc
733   ld bc,-32
734   add hl,bc
735   ex de,hl
736   ld a,(de)
737   ld c,0
738 ShiftBitsRight = $-1
739 ShiftRowsRight:
740   push hl
741   rra
742   ld b,16
743 ShiftRowRight:
744   rr (hl)
745   inc hl
746   djnz ShiftRowRight
747   pop hl
748   dec c
749   jr nz,ShiftRowsRight
750   ld bc,-16
751   add hl,bc
752   ex de,hl
753   pop bc
754   djnz ShiftRightLoop
755   ld a,(ShiftBitsRight)
756 NoShift:
757   ld hl,DispBuffer
758   ld de,$fc00+$70
759   ld bc,1024-$70
760   ldir
761   cpl
762   add a,8
763   jr z,NoShiftDelay
764 ShiftDelay:
765   ld bc,$0005
766 ShiftDelayLoop = $-1
767   djnz ShiftDelayLoop
768   dec c
769   jr nz,ShiftDelayLoop
770   dec a
771   jr nz,ShiftDelay
772 NoShiftDelay:
773   pop de
774   pop bc
775   ret
776
777
778 NUM_LEVELS = 9
779
780 Levels:
781   .db 5,2           ;5 peas, speed 9
782   .db 64,4,0        ;x,y,d
783   .db 0,0            ;field width, height
784   .db 0             ;no additional lines
785
786   .db 8,2
787   .db 4,14,$40
788   .db 128,57
789   .db 1
790   .db 28,28,100,28
791
792   .db 9,2
793   .db 4,8,$40
794   .db 128,57
795   .db 2
796   .db 28,14,100,14
797   .db 28,41,100,41
798
799   .db 9,1
800   .db 4,8,$40
801   .db 128,80
802   .db 2
803   .db 64,14,64,66
804   .db 20,40,108,40
805
806   .db 10,1
807   .db 4,8,$40
808   .db 128,90
809   .db 3
810   .db 18,20,18,70
811   .db 110,20,110,70
812   .db 18,45,110,45
813
814   .db 7,1
815   .db 64,4,0
816   .db 128,86
817   .db 6
818   .db 34,13,56,35
819   .db 34,71,56,49
820   .db 72,35,94,13
821   .db 72,49,94,71
822   .db 16,20,16,64
823   .db 110,20,110,64
824
825   .db 9,0
826   .db 4,10,$40
827   .db 128,82
828   .db 3
829   .db 0,20,74,20
830   .db 54,40,128,40
831   .db 0,60,74,60
832
833   .db 12,0
834   .db 64,4,0
835   .db 128,90
836   .db 6
837   .db 20,16,54,16
838   .db 74,16,110,16
839   .db 20,16,20,72
840   .db 110,16,110,72
841   .db 20,72,54,72
842   .db 74,72,110,72
843
844   .db 8,0
845   .db 72,52,$c0
846   .db 128,128
847   .db 13
848   .db 34,56,56,34
849   .db 34,72,56,94
850   .db 72,34,94,56
851   .db 72,94,94,72
852   .db 46,64,80,64
853   .db 22,11,22,33
854   .db 11,22,33,22
855   .db 22,95,22,117
856   .db 11,106,33,106
857   .db 103,11,103,33
858   .db 91,22,115,22
859   .db 103,95,103,117
860   .db 91,106,115,106
861
862
863
864 #include "trigtab.asm"
865 #include "line.asm"
866
867 WormMsg .db "Wonderworm!",0
868 LevelMsg .db "Level ",0
869 LivesMsg .db "Lives: ",0
870 ScoreMsg .db "Score: ",0
871 LeftMsg  .db "Food: ",0
872 HiScore .db 0
873
874 Left =$
875 Lives =$+1
876 Level =$+2
877 Score =$+3
878 DispBuffer =$+5
879
880 ScrBuffer =$8200 ;32x256 bytes
881 SinCosTable =$a200
882 WormPos = $b000
883
884 .end