pfLayer(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfLayer(3pf)NAMEpfLayer - Create, modify, and query layer nodes for decals and coplanar
polygons.
FUNCTION SPECIFICATION
#include <Performer/pf/pfLayer.h>
pfLayer::pfLayer();
static pfType * pfLayer::getClassType(void);
void pfLayer::setMode(int mode);
int pfLayer::getMode(void);
void pfLayer::setPlane(pfPlane *plane);
pfPlane * pfLayer::getPlane(void);
void pfLayer::setBase(pfNode *base);
pfNode * pfLayer::getBase(void);
void pfLayer::setDecal(pfNode *decal);
pfNode * pfLayer::getDecal(void);
PARENT CLASS FUNCTIONS
The OpenGL Performer class pfLayer is derived from the parent class
pfGroup, so each of these member functions of class pfGroup are also
directly usable with objects of class pfLayer. This is also true for
ancestor classes of class pfGroup.
int pfGroup::addChild(pfNode *child);
int pfGroup::insertChild(int index, pfNode *child);
int pfGroup::replaceChild(pfNode *old, pfNode *new);
int pfGroup::removeChild(pfNode* child);
int pfGroup::searchChild(pfNode* child);
pfNode * pfGroup::getChild(int index);
int pfGroup::getNumChildren(void);
int pfGroup::bufferAddChild(pfNode *child);
int pfGroup::bufferRemoveChild(pfNode *child);
Since the class pfGroup is itself derived from the parent class pfNode,
objects of class pfLayer can also be used with these functions designed
for objects of class pfNode.
pfGroup * pfNode::getParent(int i);
int pfNode::getNumParents(void);
Page 1
pfLayer(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfLayer(3pf)
void pfNode::setBound(pfSphere *bsph, int mode);
int pfNode::getBound(pfSphere *bsph);
pfNode* pfNode::clone(int mode);
pfNode* pfNode::bufferClone(int mode, pfBuffer *buf);
int pfNode::flatten(int mode);
int pfNode::setName(const char *name);
const char * pfNode::getName(void);
pfNode* pfNode::find(const char *pathName, pfType *type);
pfNode* pfNode::lookup(const char *name, pfType* type);
int pfNode::isect(pfSegSet *segSet, pfHit **hits[]);
void pfNode::setTravMask(int which, uint mask, int setMode,
int bitOp);
uint pfNode::getTravMask(int which);
void pfNode::setTravFuncs(int which, pfNodeTravFuncType pre,
pfNodeTravFuncType post);
void pfNode::getTravFuncs(int which, pfNodeTravFuncType *pre,
pfNodeTravFuncType *post);
void pfNode::setTravData(int which, void *data);
void * pfNode::getTravData(int which);
void pfNode::setTravMode(int which, int mode, int val);
int pfNode::getTravMode(int which, int mode) const;
Since the class pfNode is itself derived from the parent class pfObject,
objects of class pfLayer can also be used with these functions designed
for objects of class pfObject.
void* pfObject::operator new(size_t);
void* pfObject::operator new(size_t, pfFluxMemory *fmem);
void pfObject::setUserData(void *data);
void pfObject::setUserData(int slot, void *data);
void* pfObject::getUserData(pfObject *obj);
void* pfObject::getUserData(pfObject *obj, int slot);
int pfObject::getNumUserData();
Since the class pfObject is itself derived from the parent class
pfMemory, objects of class pfLayer can also be used with these functions
designed for objects of class pfMemory.
void* pfMemory::getData(const void *ptr);
pfType * pfMemory::getType();
int pfMemory::isOfType(pfType *type);
int pfMemory::isExactType(pfType *type);
const char * pfMemory::getTypeName();
int pfMemory::copy(pfMemory *src);
int pfMemory::compare(const pfMemory *mem);
void pfMemory::print(uint which, uint verbose, char *prefix,
FILE *file);
int pfMemory::getArena(void *ptr);
Page 2
pfLayer(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfLayer(3pf)
void* pfMemory::getArena();
int pfMemory::ref();
int pfMemory::unref();
int pfMemory::unrefDelete();
int pfMemory::unrefGetRef();
int pfMemory::getRef();
int pfMemory::checkDelete();
int pfMemory::isFluxed();
void * pfMemory::getArena();
int pfMemory::getSize();
DESCRIPTION
On Z-buffer based machines, numerical precision can cause distracting
artifacts when rendering coplanar geometry. A pfLayer is a node derived
from pfGroup that supports proper drawing of coplanar geometry on OpenGL
platforms.
A pfLayer can be thought of as a stack of geometry where each layer has
visual priority over the geometry beneath it in the stack. An example of
a 3 layer stack consists of stripes which are layered over a runway which
is layered over the ground. The bottommost layer is called the "base"
while the other layers are called "decals". When using certain hardware
mechanisms (PFDECAL_BASE_STENCIL) to implement pfLayers, the "base" is
special because it defines the depth values which are used to determine
pfLayer visibility with respect to other scene geometry and which are
written to the depth buffer.
new pfLayer creates and returns a handle to a pfLayer. Like other
pfNodes, pfLayers are always allocated from shared memory and cannot be
created statically, on the stack or in arrays. pfLayers should be
deleted using pfDelete rather than the delete operator.
pfLayer::getClassType returns the pfType* for the class pfLayer. The
pfType* returned by pfLayer::getClassType is the same as the pfType*
returned by invoking the virtual function getType on any instance of
class pfLayer. Because OpenGL Performer allows subclassing of built-in
types, when decisions are made based on the type of an object, it is
usually better to use the member function isOfType to test if an object
is of a type derived from a Performer type rather than to test for strict
equality of the pfType*'s.
Since pfLayer is derived from pfGroup, pfGroup API may be used to
manipulate its child list. OpenGL Performer considers child 0 to be the
base geometry and children 1 through N-1 to be decals. Decals are
rendered in order such that decal[i+1] is drawn atop decal[i]. In other
words, decal[i+1] has visual priority over decal[i] even though they are
coplanar. pfLayer::setBase and pfLayer::setDecal are convenience
routines for setting the base and decal children of the pfLayer in the
common case where there is only one decal child. pfLayer::getBase and
pfLayer::getDecal return the base and first child of the pfLayer.
The mode argument to pfLayer::setMode specifies which hardware mechanism
Page 3
pfLayer(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfLayer(3pf)
to use and is one of:
PFDECAL_BASE_DISPLACE
Use slope-based polygon displacement to slightly displace the
depth values of decal geometry closer to the eye so they have
visual priority. Each decal is displaced more than its
predecessor to properly resolve priority between decals. The
maximum number of decals is 8.
PFDECAL_BASE_DISPLACE | PFDECAL_LAYER_OFFSET
Use slope-based polygon displacement to slightly displace the
depth values of decal geometry closer to the eye so they have
visual priority. In addition, decal geometry is offset a
constant amount to eliminate anomalies caused by geometry which
is nearly perpendicular to the view. Each decal is displaced
and offset more than its predecessor to properly resolve
priority between decals. The maximum number of decals is 8.
PFDECAL_BASE_STENCIL
Use the stencil-buffer logic to determine visibility of decal
geometry. There is no limit to the number of decals.
PFDECAL_BASE_FAST
Use a decaling mechanism appropriate to the hardware that
produces the fastest, but not necessarily the highest quality,
decaling.
PFDECAL_BASE_HIGH_QUALITY
Use a decaling mechanism appropriate to the hardware that
produces the highest quality, but not necessarily the fastest,
decaling.
The decal mode may also include the PFDECAL_PLANE token OR-ed with one of
the above tokens which will enable the use of the decal reference plane
(set with pfLayer::setPlane). This can offer much higher quality of
PFDECAL_BASE_DISPLACE type layers.
The default layer mode is PFDECAL_BASE_FAST. pfLayer::getMode returns
the mode of the pfLayer.
The different pfLayer modes offer quality-feature tradeoffs listed in the
table below:
DISPLACE STENCIL (DISPLACE | OFFSET)
___________________________________________________________
Quality medium high high
Sorting enabled disabled enabled
Coplanarity not required required not required
Multipass ok not ok ok
Containment not required required not required
|
|
|
Page 4
pfLayer(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfLayer(3pf)
|
|
|
The STENCIL mechanism offers the best image quality but at a performance
cost since the base and layer geometry must be rendered in order,
obviating any benefits of sorting by graphics state offered by
pfChannel::setBinSort. When multisampling on RealityEngine, this
mechanism also significantly reduces pixel fill performance. The
performance impact is not as severe in InfiniteReality systems. An
additional constraint is that STENCILed layers must be coplanar or decal
geometry may incorrectly show through base geometry. A subtle but
important issue with STENCILed layers is that they are unsuitable for
multipass renderings (projected textures) since multiple surfaces are
visible at a given pixel. For proper results, each layer in the "stack"
must be completely contained within the boundaries of the base geometry.
The DISPLACE mechanism offers the best performance since layers can be
sorted by graphics state, because the displace call itself is usually
faster than other mode changes, and because there is no pixel fill rate
penalty when it is in use. The OFFSET mechanism adds a constant offset to
the decal geometry. This mode can be very expensive (RealityEngine) so
when using it the database should be sorted with PFSTATE_DECAL as the
first sorting key (see pfChannel::setBinSort). Both DISPLACE mechanisms
do not require that geometry within a single layer be coplanar and also
produce a single visible surface at each pixel for multipass renderings.
The main disadvantage is that decal geometry may incorrectly poke through
other geometry due to the displacement of the decal geometry. Another
disadvantage is that the maximum number of decals is 8.
The performance differences between STENCIL and DISPLACE modes are
hardware-dependent so some experimentation and benchmarking is required
to determine the most suitable method for your application.
pfLayer::setPlane sets a reference plane to be used for all geometry
under the pfLayer node. pfLayer::getPlane returns the reference plane,
or NULL if no such plane is set on the pfLayer.
NOTES
Using PFDECAL_BASE_STENCIL for pfLayer nodes requires several steps for
proper operation. First, the graphics hardware must support stencil plane
rendering. Secondly, the graphics context must be configured with at
least one stencil plane, and the lowest order bit of the allocated
stencil planes be reserved for OpenGL Performer use. pfInitGfx
configures the graphics context in just this way.
The use of displacements for rendering coplanar geometry can cause visual
artifacts such as decals "Z fighting" or "flimmering" when viewed
perpendicularly, and the "punching through" of decals that should mask
base geometry when both are viewed obliquely. The former artifact can be
eliminated by specifying PFDECAL_BASE_DISPLACE | PFDECAL_LAYER_OFFSET as
the layer mode. Subtle details of this rendering mode are described in
the pfDecal man page. If unacceptable artifacts still persist, the
Page 5
pfLayer(3pf) OpenGL Performer 3.2.2 libpf C++ Reference Pages pfLayer(3pf)
database should be modified to eliminate the need for coplanar rendering
or PFDECAL_BASE_HIGH_QUALITY should be used.
When using PFDECAL_LAYER_OFFSET, the minimum depth buffer range set with
lsetdepth must be incremented an extra 1024 * max layers so the negative
displacement of the layers does not wrap. pfInitGfx does this
automatically.
BUGS
OpenGL Performer properly renders coplanar geometry only on machines that
have a hardware stencil buffer allocated or which support displaced
polygon rendering.
SEE ALSO
pfChannel, pfDecal, pfGroup, pfInitGfx, pfLookupNode, pfNode, pfDelete
Page 6