Thousands of particles which appear to be made of light form beautiful surfaces in 3D space. We use an additive luminescent effect which creates brighter spots where particles are more concentrated. We present four examples with variations in color and filter effects. Click each screen shot to open a Flash movie. Download source code from the link below.
- Download all source files corresponding to this effects: light.zip
Download the zip package linked above for the complete, well-commented, and easy to customize source code.
Particles made of light form parametric surfaces
We present four variations of a new particle example using pixel-based particles in three dimensions. This experiment is similar to our earlier pixel particle examples, but with a twist. The major difference lies in a technique which allows particles which stack on top of each other to have an additive luminescent effect. We have also made some simplifications which allow for less CPU to be used.
In our earlier examples, the particles were considered as opaque objects. Thus, when one particle was in front of another in the view plane, we needed to make sure that only the particle in front would be shown. We used a z-buffer to accomplish this type of z-sorting.
Here, however, we have done away with z-sorting (which saves some CPU), and instead we allow the brightness of overlapping particles to add together. This gives us the luminescent effect.
Comments on the code
Since much of the code here is similar to our earlier examples, we will only explain the lines of code that achieve the additive brightness effect. The coloring method we describe below produces blue pixels, which is the method used in two of the examples. The other versions have similar code but with a different coloring method.
Here is how it works. The particles are drawn to a bitmap, and they will all have the same blue hue. To draw a particle p to its view plane position (p.projX, p.projY), we will increase the brightness of the pixel in that position by an increment levelInc. We first determine the color of the bitmap at that position:
readColor = bufferBitmapData.getPixel(p.projX, p.projY);
The blue component value of this color will tell us the current brightness in this position, which will be caused by other particles which have been drawn here already. So we determine the blue component of this color with a bitwise operation, and add levelInc to this value in order to represent the increased brightness from the new particle we are drawing:
level = (readColor & 0xFF)+levelInc;
We make sure that level stays smaller than 255:
level = (level > 255) ? 255 : level;
Now we will redraw the pixel in this position with this brighter color. Using a light blue color can be done in a very CPU efficient manner using a trick involving bitwise operations. The light blue we are using will have a zero red component, and a green component which is half of the blue component. The blue component will be the level variable as we have set it above, and the green component will be 50% of the blue value. We divide level in half using a fast technique: a bit-shift operation of shifting down by one bit accomplishes the same thing as dividing by two (when we are only interested in integer outputs). Our light blue color is created as follows:
dColor = ((level>>1) << 8) | level;
Finally, we color the pixel in this position with this newly calculated color value:
bufferBitmapData.setPixel(p.projX, p.projY, dColor);
Positioning the particles
The particles in this example are given x, y, and z coordinates in space according to equations in two variables s and t. These equations determine what is called a parametric surface. See our parametric surfaces grapher to play with parametric surfaces: Parametric Surfaces in Rectangular Coordinates. We do some calculations to change viewpoint-relative coordinates which result from rotation, but the fixed x, y, and z coordinates never change. This uses less CPU compared to some of our earlier examples, where the particles were moving in (x, y, z) space while also being rotated.
Notes on the variations in the examples
The examples presented above are all very similar in terms of code behind them. Variations in coloring and filter effects produce different visual results.
Versions 1 and 4 (screen shots 2 and 4) use the blue pixel method described above, whereas version 2 (screen shot 3) uses white pixels, produced in a very similar way (examine the code). In version 3 (the first screen shot), we allow the color of the particles to slowly change over time. This adds significant CPU load, because we must do some multiplications to calculate the color every time a pixel is drawn. Thus we make use of fewer particles in this example.
There are also some variations in the filters we are using – examine the code to see how color transforms and blur filters are used both before and after drawing pixels. Version 4 (screen shot 4) has one significant difference from the other examples, in that it makes use of two bitmapData objects: one which serves as a buffer (which is not displayed) and another for the displayed bitmap. This allows us to apply some filters to the display which will not affect future updates of the buffer bitmap data. We apply a color transform which darkens but also increases the contrast of the display.
There is one more variation to note: version 2 (screen shot 3) uses some randomization in the positioning of the particles, which gives a "fuzzier" look. This is done by allowing the parameters s and t to vary randomly before they are plugged into the equations which determine (x, y, z) coordinates.
Other Flash and Math particle effects
- Astronaut - 3D Particle Effect in AS3 Flash CS4
- Flower Twist – Interactive 3D Bitmap Particles in AS3
- Nova - Cosmic Interactive Particle Effect in AS3 Flash
- Kepler's Supernova - 3D Particle Effect in AS3 Flash CS4
- A Rotating Bitmap in 3D Explodes into Particles
- 3D Particle Experiments in AS3 Flash CS3