Basic 2D Rain, Thunder and Lightning in Godot


In this post I will explain how I implemented basic 2D weather effects for FEED.

The weather effect shown above is accomplished with two components, and by changing some setting in the "DirectionalLight2D" that provides the overall lighting for every level found in FEED. We'll start with the easiest, the settings.

Darkening the Scene

This is what the scene graph for basically every level of FEED looks like. There's a DirectionalLight2D in each scene that normally acts as an ambient light source, however for the rainy levels I wanted the scene to be extremely dark. To make the normally pretty bright scenes darker, I just change the Blend Mode from Add to Subtract, and then change the value for Energy from 1.0 to around .25 or so. What this does is makes it so the DirectionalLight2D no longer brightens the scene, but instead darkens the scene. I lower the Energy value so it doesn't make everything completely black. There's plenty of other ways to achieve this affect, but I like this one because it also darkens the PointLights in the scene.

WeatherComponent

WeatherComponent is a Node that handles the thunder and lightning effect. All of the sound effects for this effect were acquired from freesound.org which is an amazing resource with a lot of great royalty free sound effects.



Above is the code in the script attached to the WeatherComponent. There is a timer called LightningTimer. When the timer times out it randomly selects a thunder sound to play. To achieve this, I simply added all of the thunder sound effects to a group called "thunder" in the godot editor and then generate a random index. More about groups here. Also upon timing out, the LightningTimer's wait time is adjusted randomly, so the timing of the lightning doesn't become predictable. To create the flash of light, the energy value for the DirectionalLight2D in the WeatherComponent (which has default settings and is different from the one that is normally present in the scene) to 1.0. Then, every single frame the energy value move towards 0 by delta. This makes it so the flash will return full darkness after 1 second. 

One thing you might have trouble with if you try to implement this effect is your lights not interacting with your ParallaxBackground. This is because the ParallaxBackground is set to a light-layer of -100 by default. To have the flash of light also light up the ParallaxBackground, set the Layer Min value to -100 or less:


RainComponent

I looked for weather particle tutorials and plugins on youtube and in the asset store but could not find anything for 2D, so I had to make my own. I ended up doing a lazy approach that is definitely inefficient performance-wise, but it seems that the game still runs extremely fast so it must not be too much of a problem at this scale.


The RainComponent is a Node2D with just one timer attached. The timer is set to a very low wait_time of 0.15

As you can see in the above built-in script, the RainComponent spawns rain_drop_num number of raindrop instances between a random width and height upon every timeout of the rainDropTimer. 


The raindrop line

The rain_drop scene is just a diagonal Line2D with this built-in script:


All this script does is move the line diagonally at the speed of gravity, and despawn the raindrop if it has fallen too far.

Obviously this is a very lazy approach and there are billions of different ways to make this more efficient and visually interesting, but for how simple it is, I think it turned out great!

Get FEED

Leave a comment

Log in with itch.io to leave a comment.