OpenGLContext.passes.renderpass
Default rendering-algorithm implementation
This module provides the default rendering algorithm
implementation, including the opaque, transparent and
selection rendering-passes. The classes here are also
used as the base classes for the shadow/passes.py
module which implements the shadow-casting rendering
algorithm.
Classes
class _defaultRenderPasses(
object
):
class OpaqueRenderPass(
VisitingRenderPass
):
Opaque geometry rendering through scenegraph visitation
The opaque rendering passes is the most "normal"
of the rendering passes. It basically just uses
the RenderVisitor implementation to render the
scenegraph or Context.
The OpaqueRenderPass uses the context's shouldRedraw
and suppressRedraw methods to determine whether or not to
render itself, (and to let the context know that it has
rendered). This is not ideologically pure, as potentially
there could be another rendering pass responsible for
"visible" rendering. It is, however, practical for now.
Note:
The OpaqueRenderPass registers objects for the
TransparentRenderPass, so the TransparentRenderPass
cannot operate without a preceding OpaqueRenderPass.
class OverallPass(
object
):
Representation of an overall rendering pass
The OverallPass object represents a collection of sub-passes
which, together, are considered a full rendering cycle. The
OverallPass stores information about the entire rendering
cycle, with the attributes of the OverallPass available to
each sub-pass (and thereby to rendering code).
Attributes:
context -- reference to the client Context object
into which this pass is being rendered
lightPaths, viewPaths, backgroundPaths, fogPaths --
nodepath objects for each active object of the given
node-types found during the initial "findBindables"
"rendering" pass which is run before any of the
regular render-passes.
See:
findBindables
RenderVisitor.SceneGraphLights
RenderVisitor.SceneGraphBackground
- transparentObjects
- sequence of transparent object records registered (normally by OpaqueRenderPass) for processing (normally by TransparentRenderPass). See: addTransparent() getTransparent()
## Note: the following are not considered particularly useful
# and may disappear at some point in time
startTime -- the startTime value passed to the initializer,
or the value of time.time() during initialization if
there was no value
viewport -- glGetIntegerv( GL_VIEWPORT )
-> (x,y, width, height)
projection -- glGetDoublev( GL_PROJECTION_MATRIX )
-> 4x4 float matrix
modelView -- glGetDoublev( GL_MODELVIEW_MATRIX )
-> 4x4 float matrix
__call__(
self
)
Render the pass and all sub-passes
Reports whether or not there was a visible change
__init__(
self
,
context
= None
,
subPasses
= ()
,
startTime
= None
)
Initialize the OverallPass object
- context
- the client Context node
- subPasses
- sequence of sub-pass RenderPass objects
- startTime
- optional starting time value
addTransparent(
self
,
token
,
matrix
= None
)
Register object for transparent rendering pass
- token
- opaque pointer to an object to be rendered during the transparent rendering pass
The current model-view matrix will be stored with
the token for use during the transparent rendering pass
findBindables(
self
)
Calculate and store nodepath(s) for active bindable and light nodes
See:
RenderVisitor.SceneGraphLights
RenderVisitor.SceneGraphBackground
Callable list of sub-passes with associated OverallPass
The PassSet is called once per render-cycle,
and is responsible for creating the OverallPass
which does the actual rendering. It simply
creates the OverallPass with the given sub-passes
and calls the OverallPass, returning the result.
class RenderPass(
object
):
A particular pass of a particular rendering mode
Most RenderPass instances are actually VisitingRenderPass
instances, with the notable exception of TransparentRenderPass
objects.
Attributes (normally class-static):
transform -- whether to do transforms, most do
- visible
- whether there is any visible change to the buffer (use textures, colours, etceteras)
- transparent
- whether is a transparent-rendering pass
- selectNames
- whether should push/pop selection "names"
- selectForced
- whether we are currently in forced- selection mode
- stencil
- whether we are rendering into the stencil buffer
- lighting
- lighting is being used (most opaque/ transparent, but not selection)
- lightingAmbient
- whether ambient lighting should be used
- lightingDiffuse
- whether diffuse lighting should be used (non-ambient)
Note:
The RenderPass will look up any missing attributes
in the OverallPass object, so effectively the RenderPass
has all of the attributes of the OverallPass which
is passed to the initializer.
Note:
This class is a consolidation of the RenderPass and
RenderMode classes in OpenGLContext version 1.0
__init__(
self
,
overall
,
passCount
= 0
)
Initialise the per-mode render-pass object
- overall
- the OverallPass instance which is driving this RenderPass instance. Attributes of the OverallPass are made available via the __getattr__ hook.
- passCount
- the index of this pass within the OverallPass, an integer representing the number of passes which have come before us.
The initializer calls OnInit when it is finished
to allow for easy sub-class customization.
class SelectRenderPass(
VisitingRenderPass
):
glSelectBuffer-based selection rendering mode
This is an implementation of glSelectBuffer-based
selection modes. It allows for projecting multiple
"pick" events into the scenegraph. The
implementation tries to be as general as possible.
The RenderVisitor.Grouping method takes care of
calling the Grouping nodes' pushName method to
generate the name stack which is reported by the
SelectRenderPass.
See:
OpenGLContext.events.mouseevents
OpenGLContext.context.getPickEvents
OpenGLContext.context.addPickEvent
Note:
Each pick event causes a complete render-traversal,
which, if there are a lot of pick-events, can
dramatically slowdown your frame rate! There
should be some logic to try to minimize these
events, but I haven't come up with a generalized
solution to the problem.
Note:
Pick events are registered and accessed from the
Context object. The SelectRenderPass can deal
(and it does deal only in the current implementation)
with events which were generated/registered either
by a previous render-pass, or between rendering
passes.
Attributes:
bufferSize -- the size of the Name buffer used
to store the name-stack which will be reported.
The default value, 512, is somewhat wasteful
but does allow for fairly deep scenegraph's.
matrixSize -- the pixel-size dimensions of the
pick matrix (default is 2,2) used
pickPoint -- stores the current pick-point for the
selection rendering pass.
selectable -- mapping from "name" (OpenGL integer name)
to selectable Node (an opaque object reference) used
to provide easy access to the list of selected nodes.
See:
addSelectable()
__call__(
self
)
Render geometry once for each pick-event to be serviced
This is the actual implementation of the glSelectBuffer-
based selection code. It is fairly standard OpenGL
selection code.
We take all of the events which have the same picking-point
and render them together (since they have the same picking
characteristics).
For each picking-point, we set up the constrained picking
matrix and results array in our ContextSetupDisplay/
PickProjection methods, which are visited by the standard
RenderVisitor algorithm.
The visiting code, particularly RenderVisitor.Grouping,
pushes the appropriate names onto the name stack during
rendering, filling the results array as appropriate.
After visiting the entire scenegraph, we retrieve the results
from the name-stack and dispatch the events to their
appropriate handlers.
XXX
Really the event handling should not be going on here,
instead the events should be added to a queue to be
processed after the RenderPass has completely finished,
and the ContextLock has been released (but the scenegraph
lock has been re-acquired).
PickProjection(
self
)
Setup the constrained picking matrix and result buffer
We set up the view frustum to be a
box centered around the picking point of size
self.matrixSize, projecting back into the screen
from our current viewpoint.
We then set up the selection buffer into which
our results will be saved, and then switch to
selection-mode rendering.
class TransparentRenderPass(
RenderPass
):
Blend-based transparent/translucent geometry rendering
This is an implementation of transparent geometry rendering
which, although not rigorously generalized, should provide
basic functionality.
XXX What is wrong with the implementation?
Properly done, a transparent-rendering algorithm should
sort all polygons of all transparent objects together
with each vertex of each polygon projected, and any
intersecting polygons tesselated to form polygons which
are unambiguously in front of or behind every other
polygon.
I haven't implemented that algorithm, mostly because it
is a great deal of work for a fairly minimal payback
given relatively infrequent occurrence of intersecting
transparent geometry.
There is a further problem when doing stencil-shadow
rendering, in that the multi-pass rendering does not
have proper depth information. I haven't come across
a decent explanation of how to implement support for
this, so I haven't done so.
__call__(
self
)
Render all registered transparent objects
Objects are projected into screen coordinates,
sorted according to their local origin depth,
then rendered with the model view matrix active
at transparent-object registration (during the
OpaqueRenderPass).
See:
OverallPass.addTransparent
OverallPass.getTransparent
ContextRenderSetup(
self
,
node
)
Set up the context for rendering prior to scene rendering
Note:
Although this is the same name as a customization point
for the RenderVisitor API, this object is not a
RenderVisitor. This method is called directly by the
__call__ method.
ContextSetupDisplay(
self
,
node
)
Establishes rendering parameters for the rendering pass
This particular transparent-geometry-rendering algorithm
uses glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA),
which requires back-to-front sorting of geometry to
produce proper results. It is one of the most
reliable methods for producing transparent geometry
effects.
Note:
Although this is the same name as a customization point
for the RenderVisitor API, this object is not a
RenderVisitor. This method is called directly by the
__call__ method.
ContextShutdown(
self
)
Clears the transparency-specific rendering parameters
Called after the entire rendering pass has completed,
this method is responsible for "cleaning up" after the
transparent-rendering pass. It also clears the list
of transparent objects build up by the OpaqueRenderPass.
Note:
Although this is the same name as a customization point
for the RenderVisitor API, this object is not a
RenderVisitor. This method is called directly by the
__call__ method.
Render(
self
,
node
)
Render a shape node as transparent geometry
This method knows how to render a Shape node as transparent
geometry. Basically that consists of calling the geometry's
render method with transparent = 1
Note:
Although this is the same name as a customization point
for the RenderVisitor API, this object is not a
RenderVisitor. This method is called directly by the
__call__ method.
A render-pass using the (normal) scenegraph-visitor pattern
Basically, the RenderVisitor implements the rendering
algorithm and the code for common object types. The
VisitingRenderPass(es) define exceptions to the
basic algorithm.