wasm4 icon indicating copy to clipboard operation
wasm4 copied to clipboard

Palette does not work as expected

Open ttulka opened this issue 2 years ago • 11 comments

Consider this AS code:

import * as w4 from "./wasm4";

store<u32>(w4.PALETTE, 0xe0f8cf, 0);    // light
store<u32>(w4.PALETTE, 0xe30000, 1);    // red
store<u32>(w4.PALETTE, 0x306850, 2);    // green
store<u32>(w4.PALETTE, 0x000000, 3);    // black

export function update (): void {
  // nothing here
}

I would expect the background colored in light green, but some kind of violet appears:

image

Works fine when the other three colors are not set.

ttulka avatar Aug 20 '21 17:08 ttulka

Hmm, it turns out the 3rd param to store is in bytes and not in elements. So it should be:

store<u32>(w4.PALETTE, 0xff0000, 0);    // light
store<u32>(w4.PALETTE, 0xe30000, 4);    // red
store<u32>(w4.PALETTE, 0x306850, 8);    // green
store<u32>(w4.PALETTE, 0x000000, 12);    // black

I'll update the docs accordingly.

aduros avatar Aug 20 '21 19:08 aduros

Yeah, it is not very use-friendly... What about making it explicit that only four colors are supported?:

store<u32>(w4.PALETTE_1, 0xff0000);    // light
store<u32>(w4.PALETTE_2, 0xe30000);    // red
store<u32>(w4.PALETTE_3, 0x306850);    // green
store<u32>(w4.PALETTE_4, 0x000000);    // black

Some more high-level API wouldn't be quite bad, too:

w4.setPallete(0xff0000, 1);
w4.setPallete(0xe30000, 2);
w4.setPallete(0x306850, 3);
w4.setPallete(0x000000, 4);

Or even?:

w4.setPallete1(0xff0000);
w4.setPallete2(0xe30000);
w4.setPallete3(0x306850);
w4.setPallete4(0x000000);

// or...

w4.setPallete(0xff0000, 0xe30000, 0x306850, 0x000000);

ttulka avatar Aug 21 '21 07:08 ttulka

PALETTE1 to PALETTE4 sounds good!

I think we should also ask the AssemblyScript folks if there's a bug with the 3rd param to store. This documentation seems wrong https://www.assemblyscript.org/introduction.html#low-level-perspective

aduros avatar Aug 21 '21 17:08 aduros

documentation seems wrong

Could you collaborate more?

The AS community is very active on Discord, that would be the best plate where to ask.

ttulka avatar Aug 21 '21 18:08 ttulka

Could you collaborate more?

In the store() example at that link, the 3rd param should be 32 instead of 8 to match the C example... I'll ping Discord about it.

aduros avatar Aug 21 '21 19:08 aduros

Opened https://github.com/AssemblyScript/assemblyscript/issues/2044

aduros avatar Aug 21 '21 19:08 aduros

Cool!

ttulka avatar Aug 21 '21 20:08 ttulka

So unfortunately the AS behavior is intended and the documentation was just wrong. I changed the WASM-4 documentation to use sizeof() to calculate the array index positions. Let's let that sit for a bit and see how it feels before adding PALETTE1-4.

aduros avatar Aug 23 '21 17:08 aduros

In Snake, I have already used

store<u32>(w4.PALETTE, 0xe0f8cf, 0 * sizeof<u32>());

But I find it plain ugly. Especially in JS-related languages such as AS, things like sizeof are very alien.

Another benefit of using PALETTE1-4 would be preventing developers from writing:

store<u32>(w4.PALETTE, 0xe0f8cf, 5 * sizeof<u32>());

It is really not a big deal, but IMHO it would increase the Developer Experience.

What speaks against that?

ttulka avatar Aug 23 '21 17:08 ttulka

There are a lot of another ways to damage WASM memory. You can wrap pallete inside your app on AS like this (you can remove trash code, this is generic pointer):

https://github.com/AssemblyScript/assemblyscript/blob/main/tests/compiler/std/pointer.ts

eXponenta avatar Sep 04 '21 22:09 eXponenta

It should be

store<u32>(w4.PALETTE, 0xe0f8cf, 0 * sizeof<u32>());    // light
store<u32>(w4.PALETTE, 0xe30000, 1 * sizeof<u32>());    // red
store<u32>(w4.PALETTE, 0x306850, 2 * sizeof<u32>());    // green
store<u32>(w4.PALETTE, 0x000000, 3 * sizeof<u32>());    // black

MaxGraey avatar Sep 05 '21 11:09 MaxGraey