Can somebody explain masks to me?

For the next release of the Arduboy2 library, I’ve changed the characters used to represent the bits in the Sprites function example patterns:
- = 0
# = 1

I hope this makes things clearer.

1 Like

Is there a reason for not using 0 and 1 in the examples?

Because 0 and 1 makes it harder to see visually.

1 Like

You should probably add a legend now if we’re making this big a deal of this.

I did add a legend, and a note at the end of the documentation for the Sprites class.

The changes can be seen in the Arduboy2 master branch on GitHub (not released yet).

1 Like

Great job! Maybe link from the header file to Pharap’s answer too? It (and the others replies) contains a lot of helpful stuff!

1 Like

The documentation in the headers is meant to be a reference, not a tutorial. A simple internet search for “bitmap mask” would give the info.

True, but it might be worth at least mentioning that the mask is and-ed with the buffer and then the sprite is or-ed on top.

That’s probably more straight forward and potentially easier to understand than the diagram for anyone who knows how bitwise operations work (i.e. the kind of people who would be referring to the documentation rather than reading a tutorial).

(Granted someone could read the cpp to find that out, but having that mentioned in the brief (and thus the doxygen-generated documentation) would save time.)

Personally, I find the “and-ed then or-ed” explanation harder to understand than

Bits set to 1 in the mask indicate that the pixel will be set to the value of the corresponding image bit. Bits set to 0 in the mask will be left unchanged.

@ulfben seemed to understand the and-or explanation better, and I must admit that’s the explanation that has worked for me in the past (which is why I presented that explanation in the first place).

Totally. And if I might add something, a problem with this line:

… is that it assumes familiarity with the screen buffer and draw order. It does not actually explain what is “left unchanged”. Pharhap’s bitwise explanation was explicit about source data and destination, which helps a lot.

That said: bitwise operations will be beyond most beginning programmers, which is why the added image example from Wikipedia is so great. It demonstrates concretely what a binary mask accomplishes.

I would also assume many of us come from other platforms and might have very different experience of what “mask” means. Personally I come from Flash / Air, GameMaker and plain SDL (whose closest equivalent would be SDL_SetColorKey). So a brief explanation of what masks mean to Arduboy2 is probably not out of place, even in the reference.

To me, right now, a mask allows me to “cut holes” in my bitmaps. :slight_smile:

1 Like

That’s a very valid point, upon re-reading it I can see how it’s a bit ambiguous.

Hrm, I agree that bitwise operations might be beyond an absolute beginner (though I’d hope they’d be reasonably early in a beginner’s “to learn” list given how significant they are, especially for optimising on less powerful hardware), but MLXXXp is right in that the library documentation isn’t aimed at beginners, it’s aimed at minimum towards people who already know how to program and are just looking for library specifics.

The wikipedia could be linked as a ‘see also’ I guess.
(I must admit I wish more documentation would include diagrams, though that’s not always practical.)

Perhaps to cover all bases someone ought to make a tutorial for the forum (assuming there isn’t already one in the magazine), to break it down for beginners.
(If I can’t find one I might contemplate making one myself when I’ve got less concurrent projects.)

It’s a bit of a strange way of thinking about it, but a somewhat accurate analogy nonetheless.

Bitmasks for images (and technically even for general purposes) are analogous to the use of paper and masking tape when painting things.

You could also think of them as stencils.

Sidenote: I too have used SDL2. It’s a nice library.

I guess I assumed that since all drawing operations are performed on the screen buffer (which is then physically displayed using display()), it would be understood that “left unchanged” implied the screen buffer. The fact that the image and mask are in program memory, thus can’t be changed, also implies the buffer.

However, I can make it more explicit. I can also add the “ANDed then ORed” description.

How does something like this sound?

Bits set to 1 in the mask indicate that the pixel in the buffer will be set to the value of the corresponding image bit. Bits set to 0 in the mask will leave the corresponding bit in the buffer unchanged. The actual logic used is: The buffer is modified by having each buffer bit ANDed with the corresponding mask bit then each resulting buffer bit is ORed with the corresponding image bit.

I would also add equivalent “logic point of view” descriptions to the other Sprites functions.

That might be a nuance of the domain.
Anyone coming from software development would be used to images/sprites/textures being in RAM (and thus modifiable). The Arduboy’s progmem sprites are quite exceptional in the grander scheme of things (more so than bitmasks).

It’s just ocurred to me that actually masks on the Arduboy are the inverse of what masks normally are.

Checking the source code confirms that the Sprites library actually inverts the mask bits before performing the typical and-or operation.

i.e. *buffer &= ~(*mask); *buffer |= *image; rather than wikipedia’s example of *buffer &= *mask; *buffer |= *image;.

I’m assuming that was to facilitate the practice of using a sprite as its own mask (in which case the more traditional method would be unsuitable).

@ulfben that means swap the black and white around in Wikipedia’s example.
If you’ve already got your masks made, just invert the colour.

1 Like

Wouldnt this be great in an Arduboy Magazine article? :wink:

1 Like

Page 33 of Volume 7 has an article on Sprites and masking.


Page 33, Volume 7. For visitors who don’t know about Arduboy Magazine yet.


That complicates the logic description a bit (no pun intended). I think it may be best to just leave only the current descriptions but clarify that the buffer is what’s being altered.

Although I’d like to keep the Doxygen formatted comments in the Arduboy2 headers more or less a technical reference, I can add more detailed documents as separate pages in the Doxygen output, as is done with having the README file be the home page, and including the LICENSE.txt file.

So @Pharap, if you or anyone else would like to write something like this, I’d consider adding it to the Arduboy2 library documentation created by Doxygen. The article can be formatted using markdown.

Hey @FManga what is this image from???


1 Like

It’s a random character generator for a game I’m making.

1 Like