Log In  

As stated in the title, you can now use up to 32 colors at the same time in pico-8 now.

The feature was revealed by Zep in this thread: https://www.lexaloffle.com/bbs/?tid=38555

This makes all the suggestions I gave in that thread possible and more.

You can't simply use all colors all over the screen though. You have 2 screen palettes and you basically have to select which palette you will use on each drawn line on the screen. In the gif above, the screen is divided into 2 halves, each with its own palette.

Palette Scanlines

Here is the code I used for both screen palettes:

pal((
{
[0]=128+9,9,1,128+12,
13,12,6,7,
8+(curr_shield==6 and 128 or 0),2,128+10,128+11,
128+15,10,4,15}),1)

--enable 2nd screen palette
poke(0x5f2c,0x40)
--values 0x10 and 0x30 to 0x3f change the efffect
poke(0x5f5f,0x10)
--new colors on the affected line
for i=0,15 do
 poke(0x5f60+i,({[0]=2,0x8d,1,0x81,0x8d,0x8c,0x86,0x87,0x88,0x81,3,0x83,0x86,0x8a,0x82,0x87})[i])
end
--0x5f70 to 0x5f7f are the 16 sections of the screen
--0xff is the bitfield of which of the 16 line of the section are affected
for i=9,15 do
 poke(0x5f70+i,0xff)
end

The first pal() is to set the game's screen palette. Nothing new here.

poke(0x5f2c,0x40) enables the 2nd palette. This is the same address that changes screen modes (rotated, stretched, mirrored). You can add these effects as usual, so 0xc5 (0x40+133) will rotate the screen and enable the 2nd palette. See the wiki for all effects.

Pokes 0x5f60 to 0x5f6f is where the 2nd screen palette is stored.

The last poke is a bit more complicated: each address from 0x5f70 to 0x5f7f is a section of the screen. 0x5f70 is the first 8 lines, 0x5f71 is the next 8, all the way to the bottom, 0x5f7f. The value you insert in the address is a Whitfield for the 8 lines of that section. 0b1 will affect the first line, 0b11 will affect the fist two lines, 0b1010101 will intercalate the lines between the two palettes, and 0b11111111 (or 0xff) will change all lines in the section.

With this, you can select either palette for all lines on the screen. But what if you want to use columns instead of horizontal lines? Like mentioned before poke(0x5f2c,0xc5) will both rotate the screen and enable the 2nd palette. If you rotate the sprites to compensate the screen rotation you can have something like this:

Each character has their own palette!

CRT effect

Gradient Fill

If you poke(0x5f5f,n) with values between 0x30 and 0x3f, you'll have a different effect. The color corresponding to the last digit of the address will be swapped for a gradient of colors. Each of the 16 sections will be swapped for a different color (pokes 0x5f60 to 0x5f6f). An example will make it clearer:

Here the black background of the game was swapped for a gradient of the 16 basic colors, using the code below:

poke(0x5f2c,0x40)
poke(0x5f5f,0x30)
for i=0,15 do
 poke(0x5f60+i,i+128)
end

So what does the 0x5f70 address do in this mode? Now each bit determines if that particular line will use the corresponding 0x5f6n color or 0x5f6n+1. Adding the code below will produce the following effect:

for i=0,15 do
 poke(0x5f70+i,0xff)
end

This might seem a bit unimpressive at first, but remember that you are free to use any of the 32 colors in this gradient, not only the ones you're using currently on the screen. This can be used to add colors to a platformer background or background effects in a shmup for instance. Here is a quick example:

If you look closely the game uses all 15 colors in the foreground and UI except for color #12 (light blue). The light blue is used for the gradient, using the regular colors 0, 1, 12, 6 and 7 and also 0x81 and 0x8c from the alternate palette (18 total colors). Here's another example using 21 colors:

Here is the code for this gradient. Just swap the colors for whatever you like :)

poke(0x5f2c,0x40)
--swap 0x3c for 0x3n where n is the color that will be swapped for the gradient
poke(0x5f5f,0x3c)
for i=0,15 do
 --put the gradient colors in the table below:
 poke(0x5f60+i,({[0]=0x82,0x82,0x84,0x84,4,4,0x89,0x89,0x8e,0x8e,0x8f,0x8f,15,15,0x87,0x87})[i])
end
for i=0,15 do
 poke(0x5f70+i,0xaa)
end

That's all I have for now. Have fun!

P#78518 2020-06-25 22:17 ( Edited 2020-06-28 23:31)

2

Thanks for the followup post! Great stuff as always.

P#78521 2020-06-25 22:40
1

Agreed. Thank you for taking the time to write this up, @BoneVolt! 🤓👍

P#78621 2020-06-28 16:28

[Please log in to post a comment]

Follow Lexaloffle:        
Generated 2020-07-15 11:44 | 0.023s | 4194k | Q:14