Thursday, August 7, 2014

Masking - Take 1

Good morning!

Today I'd like to focus on doing masking. Masking is, by definition, applying the alpha of one image multiplicity to the alpha of another image. To explain this simply, it just means that an additional layer of alpha is applied to an image (even if that image already has an alpha channel), and will only allow that image to show through wherever the alpha is greater than 0 on the mask.

I've already whipped up an example, which I was surprised to find was much simpler than I had expected. As it turns out, the guys who work on Pygame recently added a feature to the surfarray sub-module to allow users to directly reference the alpha pixels of a surface in the form of an array. This is an extremely fast operation since it's merely referencing the alpha values rather than copying them. The fact that they're being referenced is also very useful since any changes done to the values in that array immediately show on the surface.

What I've done is generated the alpha-arrays for both the masked layer and the masking layer and multiplied the masking layer's alpha-array to the masked-layer's alpha array. I then made sure to delete those arrays, since the surfaces remain locked as long as those arrays exist.

        masked_alpha = pygame.surfarray.pixels_alpha(self.output_layer)
        mask_alpha = pygame.surfarray.pixels_alpha(self.mask_layer)

        masked_alpha *= mask_alpha

        del masked_alpha
        del mask_alpha


The result is shown in the image below. The order is masked layer, masking layer, output layer.


For the most part, this does the job as described, but if you look carefully you can see that there's some strange artifacts showing up in the output layer. It's really unfortunate that those are showing up, since this solution is near perfect for what I am doing. Unfortunately, those stupid artifacts are reason enough to look for another solution (or simply a fix to this existing solution), which is why this post is titled "Take 1." I'll see what I can figure out.



No comments:

Post a Comment