Mana
Mana

Reputation: 382

How to change the saturation and overlay of a sprite in Godot

I have been planning to change my sprite to a bit darker color through changing saturation and hue values. But it seems very tricky to do so as the Godot modules only talk about changing the color of a sprite though the modulate option like this:

node.modulate= Color(0, 50, 2,0.5)

Doing so is changing the entire sprite to a new color whereas I just want to make the existing colors to a bit darker color the way we do in Photoshop using "Curves" or "Levels" - but not as refined. Any rudimentary method would also help.

Currently, I can only do "Color Overlay" without changing the opacity. Any method of adding a color overlay with opacity change would be helpful as long as it doesn't change the opacity of the entire sprite but just the overlay color.

I am working on a 2D game with imported PNG Sprites. If any more information is required, I'll be happy to provide it.

Additional Information -

What my sprite looks like

enter image description here

I want to make it darker through code twice like this -

enter image description here enter image description here

By doing node.modulate= Color(0.0, 0.0, 0.0,1) it becomes like this - enter image description here

The reason why I'm avoiding to do this manually because I have too many sprites and doing this for all of them will be tedious.

Upvotes: 6

Views: 9017

Answers (1)

hola
hola

Reputation: 3500

Example color difference image

Here's two examples of how you can darken a sprite via code.

The first method is by using self_modulate. Modulation is calculated by multiplying the modulation value by texture color value. This shows that modulation of (1, 1, 1, 1) is the same as the original texture. A modulation of (0.5, 0.5, 0.5, 1) halves the texture color making it darker like it has a half opacity black overlay.

# On a node that extends CanvasItem
self_modulate = Color(0.5, 0.5, 0.5, 1.0)

The second method is to subtract the texture value by a constant. This creates a texture that's more saturated but darker.

The shader code:

shader_type canvas_item;

uniform float difference: hint_range(0.0, 1.0) = 0.0;

void fragment() {
    vec4 tex = texture(TEXTURE, UV);
    COLOR.rgb = tex.rgb - vec3(difference);
    COLOR.a = tex.a;
}

The other code:

# On a node that extends CanvasItem
material.set_shader_param('difference', 0.3)

These effects can be combined to produce the desired result. Play around with the shader to produce a better result.

Hope this helps.

Upvotes: 10

Related Questions