Graphics Reference
In-Depth Information
and finding the min and max X and
Y
values of the eight resulting coordinates. Figure 11.9
illustrates this process.
This process can be optimized if it is assumed that the projection is perspective, and
that it is symmetrical with respect to the camera's
X
and Y axes. In this case, we can deter-
mine if the minimal or maximal
X
or
Y
value will be on the face of the box closest to the
camera, or on the face of the box farthest from the camera, based on the view-space
X
and
Y coordinates of the sphere. The code in Listing 11.14 uses this optimization to determine
the final screen-space rectangle that will be passed to the ID3D11DeviceContext::RSSet
ScissorRects method.
D3D11_RECT ViewLights:
:CalcScissorRect(
const Vector3f&
lightPos,
float
lightRange )
{
// Create a bounding
sphere
for the light., based on the position
// and range
Vector4f centerWS
=
Vector4f( lightPos,
1.0f );
float radius
=
lightRange;
// Transform
the
sphere center
to
view
space
Vector4f centerVS = ViewMatrix
*
centerWS;
// Figure out
the
four points at the top, bottom, left, and
//
right of
the
sphere
Vector4f topVS
=
centerVS
+
Vector4f(
0.0f,
radius,
0.0f, 0.0f );
Vector4f bottomVS
=
centerVS
-
Vector4f(
0.0f,
radius,
0.0f, 0.0f );
Vector4f leftVS
=
centerVS
-
Vector4f( radius,
0.0f, 0.0f, 0.0f );
Vector4f rightVS
=
centerVS
+
Vector4f( radius,
0.0f, 0.0f, 0.0f );
//
Figure out whether we want
to
use
the top
and right from quad
// tangent to
the
front
of
the sphere, or
the
back of the sphere
leftVS.z
=
leftVS.x
< 0.0f ?
leftVS.z - radius
:
leftVS.z
+
radius;
rightVS.z
=
rightVS.x
< 0.0f ?
rightVS.z
+
radius
:
rightVS.z - radius;
topVS.z
=
topVS.y
< 0.0f ?
topVS.z
+
radius
:
topVS.z
-
radius;
bottomVS.z = bottomVS.y
< 0.0f ?
bottomVS.
z -
radius
:
bottomVS.z
+
radius;
// Clamp the
z
coordinate
to
the clip
planes
leftVS.z
=
Clamp(
leftVS.z, m_fNearClip, m_fFarClip
);
rightVS.z
=
Clamp(
rightVS.z, m_fNearClip, m_fFarClip
);
topVS.z =
Clamp(
topVS.z, m_fNearClip, m_fFarClip
);
bottomVS.z
=
Clamp(
bottomVS.
z,
m_fNearClip, m_fFarClip
);
// Figure out the rectangle in clip-space by applying the
// perspective
transform.
We assume
that
the
perspective
// transform
is
symmetrical with
respect
to
X
and Y.
float rectLeftCS
=
leftVS.x
*
ProjMatrix(
0, 0 ) /
leftVS.z;
float rectRightCS
=
rightVS.x
*
ProjHatrix(
0, 0 ) /
rightVS.z;
float rectTopCS
=
topVS.y
*
ProjMatrix(
1, 1 ) /
topVS.z;
float rectBottomCS
=
bottomVS.y
*
ProjMatrix(
1, 1 ) /
bottomVS.z;
Search WWH ::
Custom Search