PETSCII on Nexty

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

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 :

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 :

DIM x as UBYTE
DIM con,off AS UINTEGER
NextReg($4a,0)                '; trasparency fallback 
NextReg($14,0) '; trasparency global
NextReg($43,%00000001) '; ULA NEXT
NextReg($42,31) '; 255 inks
PalUpload(@Palette,0,0)
' Change character set
POKE UINTEGER 23606, @typeface-256

' init variables
DIM brd, pap, car, inv, bri AS UBYTE
'     
' ' Initialize screen
100 INK 7: PAPER 0: BORDER 0: BRIGHT 0: FLASH 0: CLS
'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
PrintPetscii:
BORDER 0 : PAPER 0 : INK 0
CLS
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
zxcol:
asm
db 0,255,137,150,138,117,74,217,141,104,177,109,146,190,143,182
end asm
Palette:
asm
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
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
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
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
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
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
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
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
zxbri:
asm
db 0,1,255,1,0,0,0,1,1,0,1,0,0,1,1,0
end asm
typeface:
asm
incbin "PETSCII_VIEW.chr"
end asm
counter:
asm
dw 0
end asm
petsciis:
asm
incbin "17.psc"
; incbin "14.psc"
incbin "15.psc"
incbin "16.psc"
incbin "collection1.petscii"
incbin "collection2.petscii"
end asm


Leave a Reply