
Sorry for that. A few days ago a post on by Carlo Santagostino Spectrum For Everyone explained how he wanted to simulate the C64 PETSCII display on the ZX Spectrum. Carlo’s implementation is quite pleasing and can be found here : http://www.santagostino.eu/commodore-petscii-reader-on-the-sinclair-zx-spectrum/
For anyone who doesn’t know PETSCII is a charset that came with the C64, Carlos explains it a bit further so I am not going to repeat that info.
Anyway, the regular Spectrum version contains a look up table to convert the C64 colours in to ZX Spectrum colours, with this is mind we should be able to adapt this to work with the Enhanced ULA of the Next.

In Carlo’s code there is a simple method to pick the ZX colour depending on the colour block data
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
FUNCTION zxcol(x AS UBYTE) AS UBYTE IF x = 0 THEN x = 0 ELSE IF x = 1 THEN x = 7 ELSE IF x = 2 THEN x = 2 ELSE IF x = 3 THEN x = 5 ELSE IF x = 4 THEN x = 3 ELSE IF x = 5 THEN x = 4 ELSE IF x = 6 THEN x = 1 ELSE IF x = 7 THEN x = 6 ELSE IF x = 8 THEN x = 2 ELSE IF x = 9 THEN x = 6 ELSE IF x = 10 THEN x = 3 ELSE IF x = 11 THEN x = 1 ELSE IF x = 12 THEN x = 7 ELSE IF x = 13 THEN x = 4 ELSE IF x = 14 THEN x = 1 ELSE IF x = 15 THEN x = 7 END IF RETURN x END FUNCTION |
This works quite straight forward but to be able to get my colours in there I will simplify this bit of code to a array in memory.
zxcol:
asm
db 0,255,137,150,138,117,74,217,141,104,177,109,146,190,143,182
end asm
The values above are the index values a the relevant C64 colour positions from 0-15. I’ve picked those colours based on looking at the C64 palette and reducing it to 9 bit Next format.
Now we have the colours we need a quick change to the code that looks up the colour, we will peek the value rather that use Boriel’s in built array access.
I also POKE screen attribute from 0-767 and this works much quicker, the overall change can be seen here :
1 2 3 4 5 6 7 8 |
FOR b=0 TO 23 con=con+4 FOR a=0 TO 31 car = PEEK (@petsciis+con) : con=con+1 poke 22528+cast(uinteger,a)+(cast(uinteger,b)<<5),car NEXT a con=con+4 NEXT b |
And the final change looks like this :
1 2 |
DIM x as UBYTE DIM con,off AS UINTEGER |
1 2 3 4 5 |
NextReg($4a,0) '; trasparency fallback <br> NextReg($14,0) '; trasparency global <br> NextReg($43,%00000001) '; ULA NEXT <br> NextReg($42,31) '; 255 inks<br> PalUpload(@Palette,0,0) |
1 2 3 4 5 |
' Change character set POKE UINTEGER 23606, @typeface-256 ' init variables DIM brd, pap, car, inv, bri AS UBYTE |
1 2 3 |
' <br> ' ' Initialize screen<br> 100 INK 7: PAPER 0: BORDER 0: BRIGHT 0: FLASH 0: CLS |
1 2 3 4 5 6 7 8 |
'slide show FOR f=0 to 15 PAPER 0: BORDER 0: BRIGHT 0: FLASH 0: CLS GO SUB PrintPetscii pause 0 NEXT f con=0 GO TO 100 |
1 2 3 |
PrintPetscii:<br> BORDER 0 : PAPER 0 : INK 0<br> CLS |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 |
brd = PEEK (@petsciis+con) : con=con+1 pap = PEEK (@petsciis+con) : con=con+1 NextReg($14,0) '; trasparency global NextRegA($4a,peek(@zxcol+pap)) '; trasparency fallback 'read col FOR b=0 TO 23 ' skip left characters con=con+4 'read line FOR a=0 TO 31 car = PEEK (@petsciis+con) : con=con+1 LET inv = 0 IF car >= 224 AND car > 0 THEN car=car-64 : inv=1 ELSE IF car >= 192 AND car < 224 THEN car=car-96 : inv=1 ELSE IF car >= 160 AND car < 192 THEN car=car-128 : inv=1 ELSE IF car >= 128 AND car < 160 THEN car=car-64 : inv=1 ELSE IF car >= 96 AND car < 128 THEN car=car+64 ELSE IF car >= 64 AND car < 96 THEN car=car+32 ELSE IF car >= 0 AND car < 32 THEN car=car+64 END IF IF car >= 181 AND car < 192 THEN POKE UINTEGER 23675, @typeface+1024 PRINT INVERSE inv;CHR$((car-181)+144); ELSEIF car >=160 AND car < 181 THEN POKE UINTEGER 23675, @typeface+768 PRINT INVERSE inv;CHR$((car-160)+144); ELSEIF car >= 32 AND car < 160 THEN PRINT INVERSE inv;CHR$(car); END IF NEXT a ' skip right characters con=con+4 NEXT b ' skip 1 line con=con+40 FOR b=0 TO 23 con=con+4 FOR a=0 TO 31 car = PEEK (@petsciis+con) : con=con+1 poke 22528+cast(uinteger,a)+(cast(uinteger,b)<<5),car '+(8*p)+ peek(@zxbri+car)*64 NEXT a con=con+4 NEXT b ' skip 1 line con=con+40 RETURN |
1 2 3 4 |
zxcol:<br> asm <br> db 0,255,137,150,138,117,74,217,141,104,177,109,146,190,143,182<br> end asm |
1 2 3 4 5 6 7 8 9 10 |
Palette:<br> asm <br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1<br> db 0,0,255,1,137,0,150,0,138,0,117,0,74,0,217,0,141,0,104,0,177,0,109,0,146,0,190,0,143,0,182,1 |
1 2 3 4 |
zxbri:<br> asm <br> db 0,1,255,1,0,0,0,1,1,0,1,0,0,1,1,0<br> end asm |
1 2 3 4 |
typeface:<br> asm<br> incbin "PETSCII_VIEW.chr" <br> end asm |
1 2 3 4 5 6 7 8 9 10 11 12 13 |
counter:<br> asm <br> dw 0<br> end asm <br> petsciis:<br> asm<br> incbin "17.psc"<br> ; incbin "14.psc"<br> incbin "15.psc"<br> incbin "16.psc"<br> incbin "collection1.petscii"<br> incbin "collection2.petscii"<br> end asm |
