Author Topic: 1986 Locomotive basic Game  (Read 409 times)

0 Members and 1 Guest are viewing this topic.

Offline Nemo59

  • CPC464
  • **
  • Posts: 29
  • Country: fr
  • CPC6128+
  • Liked: 60
  • Likes Given: 26
1986 Locomotive basic Game
« on: 19:58, 14 April 21 »

https://youtu.be/PCCIlgDdw_4


Source :


Code: [Select]
10 '================================
20 '
30 ' LES GLAXONS ATTAQUENT !!!...
40 '
45 '   G. Carpentier 1986
50 '================================
60 '
70 GOSUB 3840 ' Presentation
80 GOSUB 2760 ' Initialisations
90 score=0:perdu=0:energ=5000
100 LOCATE#2,2,12:PRINT#2," 5000":LOCATE#2,2,7 :PRINT#2," 0   "
110 '
120 GOSUB 350 ' Appel du premier tableau
130 IF perdu THEN 190 ELSE bon1=500:bon2=500:GOSUB 240:m=score
140 '
150 GOSUB 1490 ' Appel du second tableau
160 IF perdu THEN 190 ELSE bon1=1000:bon2=1000:GOSUB 240
170 '
180 GOTO 120
190 '
200 IF NOT INKEY(66) THEN END
210 LOCATE#2,2,12:PRINT#2," 0   "
220 GOSUB 3510 ' Affichage du score
230 GOTO 90
240 '
250 ' BONUS
260 '
270 CLS#3
280 LOCATE#3,10,12:PRINT#3," BONUS ";bon1:score=score+bon1
290 LOCATE#2,2,7 :PRINT#2,score 
300 IF bon2=0 THEN 330
310 LOCATE#3,10,14:PRINT#3," ENERG ";bon2:energ=energ+bon2
320 LOCATE#2,2,12:PRINT#2,energ
330 FOR i=1 TO 2500:NEXT i
340 RETURN
350 '
360 '===================================
370 '         Premier tableau
380 '===================================
390 '
400 FOR i=0 TO 11:mur(i)=23:NEXT i
410 FOR i=0 TO 5 :ob(i,4)=0:ob(i,1)=0:NEXT i
420 mur1=1:mur2=3:t=250:GOSUB 2590
430 x=15:ti=120:gagne=0:z=160
440 '
450 AFTER 6000,0 GOSUB 1260 ' Gagne   
460 AFTER 4000,1 GOSUB 1340 ' Zig-zag 
470 EVERY 100 ,2 GOSUB 1410 ' Chrono. 
480 '
490 '------------------------------------
500 '      Deplacement des objets
510 '------------------------------------
520 '
530 WHILE gagne=0
540 FOR i=0 TO 5
550   z=z+2.2
560   ob(i,4)=-ob(i,4)
570   x1=x+(NOT INKEY(k1)=-1 AND x>1)-(NOT INKEY(k2)=-1 AND x<31)
580   DI:LOCATE x,22:PRINT bl$:x=x1:LOCATE x,22:PRINT r$:EI
590   IF NOT INKEY(k3) THEN GOSUB 1110
600   ii=ob(i,1)+ob(i,3)
610   IF ii>=22 AND ii<=24 AND ob(i,0)>=x AND ob(i,0)<x+3 THEN gagne=1:perdu=-1:LOCATE x,22:PRINT"2";e$;e$;e$:FOR j=1 TO 100:NEXT j:GOTO 650
620   IF ii>=mur((ob(i,0)-1)\3) THEN GOSUB 950
630   IF ob(i,1)<>0 THEN DI:LOCATE ob(i,0),ob(i,1):PRINT" ":ob(i,0)=ob(i,0)+ob(i,4):ob(i,1)=ob(i,1)+ob(i,3):LOCATE ob(i,0),ob(i,1):PRINT g$(ob(i,2)):EI ELSE ob(i,1)=1+RND*5:ob(i,0)=3+RND*27:ob(i,2)=RND*9:ob(i,3)=1+RND*1.5
640 NEXT i
650 WEND
660 '
670 '-------------------------------
680 '        Fin tableau 1
690 '-------------------------------
700 '
710 ti=REMAIN(0):ti=REMAIN(1):ti=REMAIN(2)
720 IF NOT perdu THEN 820
730 energ=0:LOCATE#2,2,12:PRINT#2,energ
740 ' Perdu
750 LOCATE x,22:PRINT bl$
760 INK 0,1,6:INK 3,6,1
770 FOR z=10 TO 31 STEP 0.25:SPEED INK z\3,z\3:SOUND 1,0,5,18-SQR(z),0,0,z:OUT &BC00,7:OUT &BD00,30-(z-INT(z))*2:NEXT z
780 INK 0,1:INK 3,6
790 CLS#3
800 FOR i=1 TO 1000:NEXT
810 RETURN
820 FOR i=1 TO 1000:NEXT i   ' Gagne
830 PRINT#1,"0"
840 FOR i=0 TO 5
850   IF ob(i,1)=0 THEN 900
860   LOCATE ob(i,0),ob(i,1):PRINT e$
870   SOUND 2,800,10,4,3,0,3
880   FOR j=1 TO 500:NEXT j
890   LOCATE ob(i,0),ob(i,1):PRINT" "
900 NEXT i
910 pb=0:GOSUB 2440
920 CLS #3
930 RETURN
940 '
950 '-------------------------------
960 '       Destruction du mur
970 '-------------------------------
980 '
990 DI
1000 LOCATE ob(i,0),ob(i,1):PRINT" "
1010 LOCATE#3,((ob(i,0)-1)\3)*3+1,mur((ob(i,0)-1)\3):PRINT#3,"   "
1020 EI
1030 mur((ob(i,0)-1)\3)=mur((ob(i,0)-1)\3)+1:ob(i,1)=0
1040 SOUND 1,120,15,15,1,1
1050 energ=energ-100
1060 IF energ<=0 THEN ener=0:gagne=1:perdu=-1 
1070 DI:LOCATE#2,2,12:PRINT#2,energ:EI
1080 IF mur((ob(i,0)-1)\3)>=27 THEN gagne=1:perdu=-1:ti=REMAIN(1):ti=REMAIN(2):ti=REMAIN(3)
1090 RETURN
1100 '
1110 '-------------------------------
1120 '            Tir
1130 '-------------------------------
1140 '
1150 SOUND 2,800,20,4,3,0
1160 PRINT#1,"1":MOVE x*16+8,64:DRAWR 0,(z\16)*16 
1170 FOR j=0 TO 5
1180   ii=ob(j,1)
1190   IF ob(j,0)=x+1 AND ii>((352-z)\16) AND ii<22 AND ii<>0 THEN DI:LOCATE x+1,ii:PRINT e$:ob(j,1)=0:SOUND 2,800,10,4,3,0,3:score=score+10*ob(j,3):LOCATE#2,2,7:PRINT#2,score:LOCATE x+1,ii:PRINT t$:EI:GOTO 1210
1200 NEXT j
1210 DRAWR 0,-(z\16)*16
1220 PRINT#1,"0" 
1230 z=z-16:IF z<0 THEN z=0
1240 RETURN
1250 '
1260 '-------------------------
1270 '         Gagne
1280 '-------------------------
1290 '
1300 ti=REMAIN(0):ti=REMAIN(1):ti=REMAIN(2)
1310 ti=0:LOCATE#2,2,17:PRINT#2,ti
1320 gagne=2
1330 RETURN
1340 '-------------------------
1350 '   Descente en zig-zag
1360 '-------------------------
1370 FOR ii=0 TO 5
1380   ob(ii,4)=RND*3-1
1390 NEXT ii
1400 RETURN
1410 '-------------------------
1420 '         Chrono
1430 '-------------------------
1440 DI
1450 ti=ti-2:LOCATE#2,2,17:PRINT#2,ti
1460 EI
1470 RETURN
1480 '
1490 '===============================
1500 '        Tableau nr 2
1510 '===============================
1520 '
1530 mur1=17:mur2=22:t=500:GOSUB 2590
1540 x=RND*15+10:xb=x
1550 ti=200:gagne=0:perdu=0
1560 '
1570 EVERY 100,2   GOSUB 2370
1580 AFTER 10000,1 GOSUB 2160
1590 '
1600 FOR i=1 TO 1000:NEXT i
1610 LOCATE x,25:PRINT r$
1620 yb=23:xb=x+1:vy=-1:vx=0
1630 IF NOT INKEY(k1) THEN vx=-1
1640 IF NOT INKEY(k2) THEN vx= 1
1650 IF vx=0 THEN 1630
1660 '
1670 GOSUB 2010             ' Diminue energie
1680 IF energ<=0 THEN 2160
1690 '
1700 '------------------------------
1710 '   Deplacement de la balle
1720 '------------------------------
1730 '
1740 WHILE gagne=0
1750 '
1760 IF xb<2  THEN vx= 1
1770 IF xb>32 THEN vx=-1
1780 IF yb<2  THEN vy=-vy
1790 IF yb=24 AND xb+vx>=x AND xb+vx<x+3 THEN vy=-vy:SOUND 1,170,15,15,1,1:IF xb>1 AND xb<33 THEN vx=SGN(xb+vx-x-1)+(xb+vx=x+1)*vx
1800 DI:LOCATE xb,yb:PRINT" ":EI
1810 IF yb>24 THEN 1910
1820 IF TEST((xb+vx)*16-8,(25-yb-vy)*16+8)=3 THEN score=score+15:DI:LOCATE((xb+vx-1)\3)*3+1,yb+vy:SOUND 1,70,15,15,1,1:PRINT"   ":vy=-vy:LOCATE#2,2,7:PRINT#2,score:EI:IF score=m+990 THEN gagne=2:pb=-3:GOSUB 2440:ELSE 1820
1830 xb=xb+vx:yb=yb+vy
1840 DI:LOCATE xb,yb:PRINT b$:EI
1850 '
1860 x1=(NOT INKEY(k1)=-1 AND x>1)-(NOT INKEY(k2)=-1 AND x<31)
1870 IF NOT INKEY(k3) AND x>2 AND x<30 THEN x1=x1+x1:IF x1<>0 THEN SOUND 1,1900,5,13:energ=energ-10::DI:LOCATE#2,2,12:PRINT#2,energ:EI:IF energ<=0 THEN energ=0:GOTO 1920
1880 DI:LOCATE x,25:PRINT bl$:x=x1+x:LOCATE x,25:PRINT r$:EI
1890 WEND
1900 RETURN
1910 '
1920 '-----------------------------------
1930 '            Perdu
1940 '-----------------------------------
1950 '
1960 LOCATE#2,2,12:PRINT#2,"   "
1970 LOCATE#2,2,12:PRINT#2,energ
1980 LOCATE x,25:PRINT"   "
1990 IF energ<=500 THEN 2160
2000 GOTO 1590
2010 '
2020 '-----------------------------------
2030 ' Nouvelle balle.Diminue energie
2040 '-----------------------------------
2050 '
2060 SOUND 1,1900,350,13
2070 FOR ii=energ TO energ-500 STEP-5
2080   energ1=ii
2090   IF energ1<=0 THEN energ1=0
2100   DI:LOCATE#2,2,12:PRINT#2,energ1:EI
2110 NEXT
2120 FOR ii=1 TO 500:NEXT ii
2130 energ=energ1
2140 SOUND 2,800,20,4,3,0
2150 RETURN
2160 '
2170 '--------------------------------
2180 '        Duree depassee
2190 '--------------------------------
2200 '
2210 ti=REMAIN(1):ti=REMAIN(2)
2220 FOR i=1 TO 31 STEP 3
2230   FOR j=3 TO 9
2240     IF TEST(i*16+8,(25-j)*16+8)<>3 THEN 2320
2250     LOCATE i,j:PRINT"   ":SOUND 1,1900,20,15
2260     FOR ii=energ TO energ-100 STEP-5
2270       energ1=ii
2280       IF energ1<=0 THEN energ=0:GOTO 2340
2290       LOCATE#2,2,12:PRINT#2,energ1
2300     NEXT ii
2310     energ=energ1
2320   NEXT j
2330 NEXT i
2340 IF energ=0 THEN perdu=1:gagne=1:RETURN
2350 gagne=2:pb=-3:GOSUB 2440
2360 RETURN
2370 '--------------------------
2380 '        Chrono 2
2390 '--------------------------
2400 DI
2410 ti=ti-2:LOCATE#2,2,17:PRINT#2,ti
2420 EI
2430 RETURN
2440 '-------------------------
2450 '   Montee du vaiseau
2460 '-------------------------
2470 TAG
2480 FOR y=(4+pb)*16 TO 399 STEP 4
2490   SOUND 2,150,10,15,3,0,13
2500   PLOT 600,600,3
2510   MOVE (x-1)*16,y-16:PRINT" ";CHR$(248);" ";
2520   PLOT 600,600,1
2530   MOVE (x-1)*16,y   :PRINT RIGHT$(r$,3);
2540   MOVE (x-1)*16,y-16:PRINT "   ";
2550 NEXT y
2560 TAGOFF
2570 RETURN
2580 '
2590 '---------------------------------
2600 '      Dessin du mur
2610 '---------------------------------
2620 '
2630 SOUND 1,499,t:SOUND 2,500,t
2640 CLS#3
2650 PRINT#1,"1":TAG   
2660 FOR y=mur1*16 TO mur2*16 STEP 16
2670   FOR x=0 TO 30*16 STEP 16*3
2680     PLOT 600,600,2:MOVE x,y-2:PRINT CHR$(253);CHR$(254);CHR$(255);
2690     PLOT 600,600,3:MOVE x,y-2:PRINT CHR$(143);CHR$(143);CHR$(143);
2700   NEXT x
2710 NEXT y
2720 TAGOFF:PRINT#1,"0"
2730 '
2740 RETURN
2750 '
2760 '===============================
2770 ' Initialisations debut partie
2780 '===============================
2790 '
2800 DIM mur(11),ob(5,4),g$(9),nom$(9),best(9)
2810 energ=5000
2820 '
2830 ENV 1,5,1,1,10,-1,1
2840 ENT 1,5,1,1,10,-1,1
2850 ENV 2,7,-2,2
2860 ENT 2,239,20,1
2870 ENV 3,5,10,20
2880 '
2890 FOR i=1 TO 9
2900   best(i)=1000:nom$(i)="SCORE"
2910 NEXT i
2920 '
2930 MODE 1:BORDER 2
2940 INK 0,1:INK 1,24:INK 2,2:INK 3,6
2950 WINDOW#1,1,33,1,1
2960 WINDOW#2,34,40,1,25:PAPER#2,2
2970 WINDOW#3,1,33,1,25 :CLS#3
2980 '
2990 SYMBOL 253,255,128,128,128,128,128,128,255
3000 SYMBOL 254,255,0,0,0,0,0,0,255
3010 SYMBOL 255,255,1,1,1,1,1,1,255
3020 SYMBOL 250,255,3,14,63,15,3,0,3
3030 SYMBOL 251,255,255,126,255,195,255,129,195
3040 SYMBOL 252,255,192,112,252,240,192,0,192
3050 SYMBOL 249,8,8,8,8,8,8,8,8
3060 SYMBOL 248,60,126,219,219,231,126,60,24
3070 SYMBOL 247,240,240,240,240,240,248,222,207
3080 SYMBOL 246,24,60,90,255,231,60,102,195
3090 SYMBOL 245,24,60,90,255,255,36,36,102
3100 SYMBOL 244,107,62,28,28,28,28,28,8
3110 '
3120 GOSUB 3290 ' Dessin de l'ecran
3130 '
3140 r$=CHR$(15)+"1"+CHR$(250)+CHR$(251)+CHR$(252)
3150 bl$="   "
3160 b$=CHR$(15)+"3"+CHR$(231)
3170 t$=CHR$(15)+"3"+CHR$(249)
3180 e$=CHR$(15)+"3"+CHR$(238)
3190 '
3200 RESTORE 3250
3210 FOR i=0 TO 9
3220   READ encre$,car
3230   g$(i)=CHR$(15)+encre$+CHR$(car)
3240 NEXT i
3250 DATA 2,231,1,224,3,225,3,245,1,246,1,189,1,198,1,226,2,244,3,247
3260 '
3270 RETURN
3280 '
3290 '-------------------------------
3300 '     Affiche score etc...
3310 '-------------------------------
3320 '
3330 CLS#2:PEN#2,3
3340 FOR i=4 TO 14 STEP 5
3350   LOCATE#2,1,i  :PRINT#2,CHR$(150);STRING$(5,CHR$(154));CHR$(156)
3360   LOCATE#2,1,i+1:PRINT#2,CHR$(149);"     ";CHR$(149)
3370   LOCATE#2,1,i+2:PRINT#2,CHR$(147);STRING$(5,CHR$(154));CHR$(153)
3380 NEXT i
3390 LOCATE#2,4,20:PEN#2,1:PRINT#2,"^0
3400 LOCATE#2,2,21:PRINT#2,"SHIFT
3410 LOCATE#2,1,22:PRINT#2,"1<0Z - X1>
3420 PEN#2,1
3430 LOCATE#2,2,5 :PRINT#2,"SCORE"
3440 LOCATE#2,2,10:PRINT#2,"ENERG"
3450 LOCATE#2,2,15:PRINT#2,"TEMPS"
3460 PEN#2,3
3470 LOCATE#2,2,12:PRINT#2,energ
3480 LOCATE#2,2,7 :PRINT#2,score
3490 '
3500 RETURN
3510 '
3520 FOR i=1 TO 9
3530   IF score > best(i) THEN 3560
3540 NEXT i
3550 GOTO 3680
3560 PRINT#1:CLS#1
3570 CALL &BB03
3580 LOCATE#3,3,2:PRINT#3,"Enter votre nom :";:INPUT#3,no$
3590 IF LEN(no$)>10 THEN no$=MID$(no$,1,10)
3600 j=8
3610 WHILE j>=i
3620   nom$(j+1)=nom$(j)
3630   best(j+1)=best(j) 
3640   j=j-1
3650 WEND
3660 nom$(i)=no$
3670 best(i)=score
3680 '--------------------------------
3690 ' Affichage des Hi-scores
3700 '--------------------------------
3710 '
3720 CLS#3
3730 PEN 3:LOCATE 8,2:PRINT"MEILLEURS SCORES"
3740 FOR i=1 TO 9
3750   LOCATE 3 ,4+2*i:PEN 1:PRINT nom$(i)   
3760   LOCATE 23,4+2*i:PEN 2:PRINT best(i)
3770 NEXT i
3780 CALL &BB03
3790 PEN 3:LOCATE 2,25:PRINT"taper une touche pour rejouer"   
3800 K$=INKEY$:IF K$="" THEN 3800
3810 IF K$=" "THEN k1=71:k2=63:k3=21:GOTO 90
3820 IF K$="X"THEN k1=74:k2=75:k3=76:GOTO 90
3830 GOTO 90
3840 '--------------------------------
3850 '       Presentation
3860 '--------------------------------
3870 DEFINT a-y
3880 MODE 0:INK 0,1:BORDER 1:INK 1,16:PEN 1:CLS
3890 pr$="LES GLAXONS"
3900 FOR x=1 TO LEN(pr$)
3910   FOR y=2 TO 11
3915     LOCATE 4+x,y-1:PRINT" "
3920     IF MID$(pr$,x,1)<>" " THEN LOCATE 4+x,y:PRINT MID$(pr$,x,1):SOUND 3,y*250,3,13:CALL &BD19
3930   NEXT y
3940 NEXT x
3945 MOVE 112,272:DRAWR 388,0,3:DRAWR 0,-128:DRAWR-388,0:DRAWR 0,128
3950 pr$="ATTAQUENT"
3951 FOR x=6 TO 14
3952   LOCATE x,13:PRINT MID$(pr$,x-5,1):SOUND 3,250,4,12:CALL &BD19:CALL &BD19
3953   FOR y=1 TO 100:NEXT y
3955 NEXT x
3960 '--------------------------------
3970 '         Musique
3980 '--------------------------------
3990 tempo=0.6
4000 k1=71:k2=63:k3=21
4010 octave=1
4020 RESTORE 4150
4030 FOR i=1 TO 68
4040   READ pitch,duration:duration=duration/2
4050   IF NOT INKEY(76) THEN k1=74:k2=75:k3=76:CLS:GOTO 4130
4060   IF NOT INKEY(47) THEN k1=71:k2=63:k3=21:CLS:GOTO 4130
4070   freq=440*(2^(octave+((pitch-10)/12)))
4080   pitchnum=ROUND(125000/freq)
4090   SOUND 1,pitchnum,duration*tempo,13
4100   SOUND 2,pitchnum+3,duration*tempo,13
4110   SOUND 4,pitchnum/2,duration*tempo,13
4120 NEXT i
4125 FOR i=1 TO 3000:NEXT i
4130 RETURN
4140 '
4150 DATA 8,20,6,20,8,20
4160 DATA 13,20,8,20,4,20,3,20,4,20
4170 DATA 6,20,8,20,10,20,12,20,13,20,4,20,6,20
4180 DATA 8,20,9,20,3,20,4,20,6,20,8,20
4190 DATA 6,20,4,20,3,20,4,20,6,20,8,20
4200 DATA 9,20,11,20,9,20,8,20,6,20,8,20
4210 DATA 9,20,11,20,13,20,14,20,11,20,9,20
4220 DATA 8,20,10,20,12,20,13,20,15,20,16,20,13,20
4230 DATA 11,20,9,20,12,20,13,20,15,20,16,20
4240 DATA 18,20,15,20,8,20,15,20,13,20,15,20
4250 DATA 16,20,18,20,16,20,15,20,13,20,12,20,13,40,8,60,4,80,1,100
4260 END
CPC 6128+ / CPM+/ Turbo PASCAL v3
https://cpcrulez.fr/auteur-nemo59.htm

Offline Takis Kalatzis

  • CPC464
  • **
  • Posts: 36
  • Country: gr
  • Liked: 19
  • Likes Given: 6
Re: 1986 Locomotive basic Game
« Reply #1 on: 13:49, 15 April 21 »
Hello,


Looks very nice. There are some strange characters in the listing (i.e. lines 830, 1220). How do we print those?


Regards,


Takis

Offline Sykobee (Briggsy)

  • 6128 Plus
  • ******
  • Posts: 828
  • Country: gb
  • Liked: 313
  • Likes Given: 491
Re: 1986 Locomotive basic Game
« Reply #2 on: 14:07, 15 April 21 »
I guess we need to replace with the equivalent chr$(n) in the listing.

Offline Nemo59

  • CPC464
  • **
  • Posts: 29
  • Country: fr
  • CPC6128+
  • Liked: 60
  • Likes Given: 26
Re: 1986 Locomotive basic Game
« Reply #3 on: 18:41, 15 April 21 »
Hi,

Strange chraracters dont like ascii translation ;D If i remember well those characters allows to move the cursor and change colors in an easy and speed way. I remember that I spended lot of time times to speed up the Basic as far I can. 35 years ago :O
I join a .dsk with the the native glaxons.bas file here. It was writen on a cpc464
« Last Edit: 21:19, 15 April 21 by Nemo59 »
CPC 6128+ / CPM+/ Turbo PASCAL v3
https://cpcrulez.fr/auteur-nemo59.htm

Offline eto

  • Supporter
  • CPC6128
  • *
  • Posts: 296
  • Country: de
  • Liked: 198
  • Likes Given: 178
Re: 1986 Locomotive basic Game
« Reply #4 on: 11:34, 16 April 21 »
If i remember well those characters allows to move the cursor and change colors in an easy and speed way.

That would actually be a good way to use it, but in this specific case I have no idea why the control codes are used. He is using CHR$(23) + 0 or 1 to set mode 0 and mode 1. No idea why it's not simply using the mode-command.


https://en.wikipedia.org/wiki/Amstrad_CPC_character_set#Control_characters

Offline Takis Kalatzis

  • CPC464
  • **
  • Posts: 36
  • Country: gr
  • Liked: 19
  • Likes Given: 6
Re: 1986 Locomotive basic Game
« Reply #5 on: 16:12, 17 April 21 »
Well, according to the above documentation, chr$(23) does not change the screen mode, it sets the graphics ink mode:


Set graphics ink mode. 0 normal (overwrite), 1 XOR, 2 AND, 3 OR

And it also says there is no BASIC equivalent for this.

Takis

Offline Nemo59

  • CPC464
  • **
  • Posts: 29
  • Country: fr
  • CPC6128+
  • Liked: 60
  • Likes Given: 26
Re: 1986 Locomotive basic Game
« Reply #6 on: 16:48, 17 April 21 »
As far I remember I never used this to change graphic mode. The idea is more to "embed" the color of the pseudo sprites , scores, timer etc. in a string. You can also manage "pseudo sprite" bigger then one char this way with no code. I remember thats it was faster too. It avoids some code since the only thing you have to manage is where to print the char. Color is embedded inside.  If you look at the source (on the .dsk to see special chars), the animation of the aliens take very few lines.
« Last Edit: 17:04, 17 April 21 by Nemo59 »
CPC 6128+ / CPM+/ Turbo PASCAL v3
https://cpcrulez.fr/auteur-nemo59.htm