In|Framez® Papers

Rippulu

By Homam Bahnassi


This tutorial is divided into the following sections:


Skill Requirements

Good knowledge in using XSI particles, Render Tree and Render Passes.



Introduction

Ah winter... It's cold, rainy and windy out there. Many of us love this dark season, but not when it comes to simulating it in a 3D scene! It's a bad dream if we just imagine all the rain and floods that should be there, and it's a nightmare is we're to do it in 3D using standard tools.
Of course, if you have a very experienced R&D team in your company, you might be pretty safe. But for those of us who aren't so lucky, our best bet would be to find hacky ways to fake the same effects you need to achieve without needing that much of in-depth research.
Throughout this tutorial, we'll examine one method to mimic rain drops falling on water surface without using complex simulation calculations for deforming the water surface.
The result is pretty good, but of course not as perfect as a CFD simulation can be. In many times I prefer faked methods over simulations because they usually needs less hardware capabilities and so they are easier to fine tune.
So let's prepare our umbrellas for a rainy day.


Final Effect Results


Building The Water Surface

We'll start this tutorial from scratch since it doesn't contain any special models or something.
You can also load the companion scene and see the final results if you just want to follow the tutorial steps without doing it on your own.

Let's start by building the water surface, get a polygonal mesh grid and size it to some reasonable value (try 40x40). Don’t care about the subdivisions because we won't alter the grid's mesh. Give the grid a meaningful name (something like "WaterSurtace").
Add a new material to this grid and an XZ Texture Support. In the RenderTree build your favorite water surface, or use the following shader preset that I used in the companion scene.


WaterSurface::RenderTree


Our next step is to setup the rain particle cloud.


Creating the Rain Cloud

Create particles from grid and place the emitter grid above the water surface, and rotate it so the particles get emitted towards the ground. The following values were used in the companion scene:
RotX = 170
PosY = 25
Modify the emitter's size to 10x10. This will be the rain particle emitter.
In the explorer, expand the cloud node and rename both its particle type and emission properties to meaningful names (use "PEmission_Rain" for the emission property and "PType_Rain" for the particle type). This way you can edit your particles more easily even if they get crowded with other properties.
Edit the "PType_Rain" particle type parameters as shown:


Rain::ParticleType


Don't stick yourself to these settings. You can always try other combinations and still get interesting results.
Now modify the rain emission parameters as follows:


Rain::Emission


Adding Water Ripples

Here we come to the place where we add interesting behavior to our particles.
For every time a rain drop hits the water surface we'll emit a ripple sprite on top of the water surface. To do this, add the "WaterSurface" as an obstacle from "Environment > Set Obstacle" in the "Simulate" toolbar.
This command will create a new collision event for your particle cloud and opens the obstacle PPG. Modify it as shown:


WaterSurface::Obstacle


Expand the cloud node in the explorer and note the new properties that were added under "RainPType" and "ParticlesOp".
As usual, give these new properties meaningful names as following: "PEvent_RainRipples" for the new particle event and "Obstacle_WaterSurface" for the WaterSurface_Obstacles.
Open the event property and choose "Emit and Disappear" from the "Action List".
In the emission field, create a new emission property for this event.
Click the "Edit" button to open the new emission PPG. Modify the following emission parameters as following:


Ripples::Event & Emission


From the emission PPG add a new particle type by clicking the ‘New’ button that's beside the ‘ParType’ list.
Click the edit button to open the new particle type PPG. Set the following values:


Ripples::ParticleType


Here we need to add key frames for the size parameter to make the particles size grows.
Add the first keyframe at frame 1 with the size value 4, and another keyframe at frame 100 with size is 6. Now we need to change the value type in the "General" tab to "age%" in order to make each emitted particle to grow as it get older.
Now for the fading effect. This effect will make each water ripple fade gradually instead of just disappearing suddenly. So we need to do something with the color properties like what we did with the size parameter, but unfortunately because of some sort of a bug in the XSI particle system you can’t animate more than one parameter using the “Age%” value type in the same particle cloud.
Don’t be worry about it because in XSI every thing has 101 ways to get it achieved, and we’re going to do this fade effect using a RenderTree trick so let’s take a look.


Fixing the Ripples Particle Type Shader

In this section, we’ll use one great particles shader node to fix the particles fading problem we talked about above. This is the "Particle_Scalar" node which returns a wide variety of Particles Scalar information. So open a RenderTree window for the particles cloud and from the ParTypes list select the "PType_Ripples".
Expand the "Particle Shape" node, you’ll get a huge list of ports. Here, we need to drive the "Input" port (which controls the color and transparency of the particles). Since we need only to modify the transparency of the particles, we need to control only the alpha channel. This could be done by using an "RGBA_Combine" node where we can modify each color channel separately, then combine them together as a color output that can be fed to the "Input" port in the "particle_shape" node.


Ripples::RenderTree


Now we are ready to control the alpha channel of the particles. Grab a "Particle_Scalar" node and connect it to the alpha port in the "RGBA_Combine" node. Open the "Particle_Scalar" node and select "Age" from the output list. Make sure to check "Normalize" to get the age values fit in the range from 0 to 1.
Finally, modify its name to "Particle_Age" to be make it more informative in the render tree.


Ripples::Render tree


Now if you do a render test to the particles, you’ll notice that the particles are born gradually and then die suddenly, this is because the "Particle_Age" node is returning values from 0 when the particle born and fades gradually to 1 when the particle dies. This is the exact opposite of the effect we need. So we need to invert the "Particle_Age" values using a "Scalar_Invert" node.


Ripples::Alpha-to-Age Relation


You can do now a render test to see how the particle ripples are born and then gradually fade until they die.


Growing Ripples

In real world, if you take a look at a water ripple, you’ll notice that as it grows, new rings are born from its center until it fades out. In our particle system, the rings only get bigger without introducing new rings when it grows. This is another case for the "Particle_Scalar" node to fix.
Since the "Paricle_Scalar" node can return information about the particle radius, we can use this to control the number of rings in the "Paricle_Shape" node so as the particle radius gets bigger, we increase the number of rings.


Ripples::Radius-to-RingsCount Relation


In the "ripplesPType" rendertree grab a new "Particle_Scalar" and connect it to the "SineScale" port in the "Particle_Shape" node. This is the port that controls the number of rings for each particle.
Open the new "Paricle_Scalar" and select "Radius" from the Output list. Rename it to "Particle_Radius".
This is not enough because the number of rings will be fairly low since the particles radius is generally small. To fix this, we need a "Scalar_Math_Basic" node to multiply the values we get from the "Particle_Radius" node with the average rings count. So grab a "Scalar_Math_Basic" node, and insert it after the "Particle_Radius" node. Open it and change as shown:


Ripples::RenderTree


Do a render test to view the final result for the particles ripples pass. We’ll see later how we’ll render this particle type in a separate pass and use in the final renders.
Next we need to do the water splashes to complete the particle work for this scene.


Adding Water Splashes

Now it's time for the water splashes. Actually, we can do these with a new particle cloud or even build the effect in an entirely new scene since we’ll render the complete effect with multiple passes. However, this is not advisable because we’ll lose our scene's management, and may cause us much pain if we decided to modify some parameters in the base particles properties.
In XSI, we can render as many particle types separately from one particle cloud using the render passes capabilities. So we’ll continue adding new particles types and emission properties to the same particle cloud.

Select the particle cloud and add a new collision event with the same water surface. Open the new Particle Event PPG, change the Action to "Emit & Disappear", then create and edit a new Emission property as shown:


Splash::Emission


Notice that we set the "Azimuth" and "Declination" values to emit the new particles perpendicular to the water surface. It's prefered that you set simple expressions to control these parameters in relation with the Emitter orientation and obstacle’s elasticity.


Splash::Azimuth-Declination


Create a new particle type for this emission property and set its parameters as shown below:


Splash::ParticleType


We need to fade the particle splashes before they die, so open the render tree for the "SplashesPType" and build the same tree we've built before for the "RipplesPType".


Splash::RenderTree


Oh, and one more thing... In order to improve the look of the particle splash, we’ll add a "Scalar_Math_Exponent" to modify the values we get from the "Particle_Scalar".
In the "Scalar_Math_Exponent" PPG set the factor value to 0.5. This will cause the particles to fade out in a square exponent way.


Splash::Alpha-to-Age Relation


Do a render test for the new particles splashes to complete the particle work for this tutorial.
Next we’ll set the cameras and render passes for the scene to complete the effect.


Setting Render Passes

In this step we need to render-map the water ripples so we can use it lately as a bump for the water surface. However, because the render-map property in XSI doesn’t render particles, we need to do render this one manually using a separate pass.
Before we start creating the new passes, we need to set a camera for them.
Get an orthographic camera and position it exactly in the middle above of the water surface. In its properties set the "Ortho Height" to 40 which is the dimension of the water surface grid, and change "Pict. Ratio" to 1.0.
Create a new empty pass for the new camera and modify its rendering "Picture Ratio" and "Output Camera" in the "Format" tab to match the setting in the camera properties.
For "Image Resolution", choose a resolution that suffices your final rendering resolution. (a value between 512 and 1024 would be enough for most cases).
Create a new partition under the new pass and the old pass, then add the particle cloud to it. Set render/view visibility to hide for the other partition.
Finally, we need to add overrides for each render pass, which enables us to mute specific particle event.


Passes


Add an override to each cloud partition in each pass. Before you start adding parameters to these overrides, we need to create a Custom Parameters Set that contains the mute parameters for each particle events. This is because if you try to add these parameters directly, they’ll conflict with each other because they get the same parameter name under one cloud.
To fix this we use the Custom PSet trick with a simple expression linking between the mute parameter under the cloud event and the mute parameter in the Custom PSet.
Now you can add those new parameters in the new Custom PSet to the partition overrides as shown:


Overrides


To hide the rain particles, we'll add one last paremeter to the "RainDrops_Pass" only. This is the "rainPType" alpha value.
Set the overrides valus for each pass so you get in the "RainDrops" pass only the water ripples sprites and the inverse for the beauty pass.


Putting it All Together

What remains now is to render the first "RainDrops_Pass", and then add the rendered frames as a bump map to the water surface. Finally you can render the full frame effect using the other "beauty_pass".
To see also a final rendering preview of this effect, play the "RainDrops" video in the companion project.

Enjoy.