Invert sprite colors through code

G

GlitchCrew

Guest
Hello!

Is it possible to invert colors of a sprite through code? I want to achieve this result:

http://imgur.com/a/Bl8s1

I've tried using draw_set_blend_mode_ext(bm_inv_src_color, bm_inv_dest_color) but it gives strange incorrect results. Maybe I'm just using it wrong.
 
A

Aura

Guest
Depends hugely on how you're doing it. That blend mode should do what you want; try posting the complete code.

Code:
draw_self();
draw_set_blend_mode_ext(bm_inv_src_color, bm_inv_dest_color);
draw_self();
draw_set_blend_mode(bm_normal);
...should do IMO. That should make clear that if you need to draw something with the effect you want, you have draw something OVER it with the blend mode; instead of drawing itself. In you case, using a pure white shape or sprite should draw it as shown in the image you linked to.
 

jo-thijs

Member
It is possible, but it is a little more complicated than that.

The reason this doesn't work:
Code:
draw_set_blend_mode_ext(bm_inv_src_color, bm_inv_dest_color)
is because it gives this as final pixel value: (min(Rs*(1-Rs) + Rd*(1-Rd), 1), min(Gs*(1-Gs) + Gd*(1-Gd), 1), min(Bs*(1-Bs) + Bd*(1-Bd), 1), min(As*(1-As) + Ad*(1-Ad), 1))
while you want ((1-Rs)*As + Rd*(1-As), (1-Gs)*As + Gd*(1-As), (1-Bs)*As + Bd*(1-As), ...).

This is not possible by drawing 1 thing through blend mode.

Now, there are 2 ways to tackle this:
1) Use shaders, shaders can do this very easilly.
2) Use blend modes a bit more extensively.
Set the blend mode to (bm_inv_dest_colour, bm_zero) and draw a white rectangle where you will draw your inverted sprite.
This will invert the colors of the place where you drew the white rectangle.
Now set the blend mode to bm_normal and draw the sprite you want to invert.
Now, set the blend mode to (bm_inv_dest_colour, bm_zero) again and draw the white rectangle again.
This will invert everything again, resulting in the background being inverted twice and the sprite you wanted to be drawn inverted, to be inverted once.
 
G

GlitchCrew

Guest
Thank you! Your solution worked perfectly fine. I've used this code:
Code:
draw_set_blend_mode_ext(bm_inv_dest_colour, bm_zero);
draw_rectangle_colour(x-sprite_width/2, y-sprite_height/2, x+sprite_width/2, y+sprite_height/2, c_white,c_white,c_white,c_white,false);
draw_set_blend_mode(bm_normal);
draw_self();
draw_set_blend_mode_ext(bm_inv_dest_colour, bm_zero);
draw_rectangle_colour(x-sprite_width/2, y-sprite_height/2, x+sprite_width/2, y+sprite_height/2, c_white,c_white,c_white,c_white,false);
draw_set_blend_mode(bm_normal);
 
G

GlitchCrew

Guest
Okay, but how do I draw a sprite in a full white color?
 
G

GlitchCrew

Guest
Nevermind, I did this using:
Code:
    d3d_set_fog(1,c_white,0,0)
    draw_sprite_ext(sprite_index,image_index,x,y,image_xscale,image_yscale,image_angle,c_white,image_alpha)
    d3d_set_fog(0,0,0,0)
 
Top