Graphics Reference
In-Depth Information
float
GetSliceIntensity
(
float
inSampleDepth
,
float
inIntensity
,
float
inSliceIndex
)
{
int
num_depth_slices
=8;
//
<
Number of depth slices
float
sample_slice_pos
=
GetLookupDepth
(
inSampleDepth
)
(
num_depth_slices
−
1) ;
float
sample_distance
=
sample_slice_pos
−
inSliceIndex
;
float
sample_influence
=1.0
−
saturate
(
sample_distance
);
return
inIntensity
sample_influence
;
}
Listing 3.3.
Calculating the volume light intensity value for a single depth slice.
The solution we came up with is similar to the technique we used earlier to
control the amount of scattering. Instead of storing the amount of scattering at
certain depths, we will store the accumulated intensity of volumetric light over
depth in another 3D texture, which we call the
volume light intensity buffer
.
For each ray-march step we will calculate the luminance of the ray-march
sample color. We will then use the view-space depth of the sample to determine
the influence of the sample on each depth slice of the 3D texture. The intensity
value of each depth slice is then incremented by the sample's luminance scaled
by the influence.
We use the function shown in Listing 3.3 to calculate the intensity values for
the 3D texture slices. The influence the ray-march sample intensity has on a depth
slice is calculated such that the first slice closer in depth will get a linear interpo-
lated influence based on the difference of the slice index and
sample_slice_pos
.
All slices further in depth will get an influence of 1.0, and all slices closer in depth
will get an influence of 0.0.
Because the volumetric light shader is rendered in half-resolution rather than
the 1/8th resolution, we needed to reduce the number of depth slices of the
volume light intensity buffer to 8 and reduce the effective distance to 64 meters
for performance reasons. When all lights have been rendered, the volume light
intensity buffer will approximate the volumetric light intensity of all volumetric
lights occluding the scene over depth (Figure 3.19(b)).
All transparent objects rendered after the volumetric light buffer has been
composited will sample the volume light intensity buffer at the proper view-space
depth to find out how much volumetric light is in front of them. We use the
same function as shown in Listing 3.1 to calculate the 3D texture lookup depth
coordinate, but with an adjusted value for
depth_range
to account for the reduced
depth range. For the
inViewSpaceDepth
parameter we pass the view-space depth
of the transparent surface. The result of the 3D texture lookup will represent the
intensity of the volumetric light in front of the transparent surface.