From Farshid Lashkari & Robert Osfield: Added support for VERTICAL_INTERLACE and HORIZONTAL_INTERLACE

stereo modes use the stencil buffer.
This commit is contained in:
Robert Osfield
2005-10-25 15:43:04 +00:00
parent e14262df85
commit f46044084a
5 changed files with 242 additions and 14 deletions

View File

@@ -31,6 +31,60 @@
using namespace osg;
using namespace osgUtil;
static const GLubyte patternVertEven[] = {
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55,
0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55};
static const GLubyte patternVertOdd[] = {
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA,
0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA, 0xAA};
static const GLubyte patternHorzEven[] = {
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00};
SceneView::SceneView(DisplaySettings* ds)
{
_displaySettings = ds;
@@ -57,6 +111,10 @@ SceneView::SceneView(DisplaySettings* ds)
_activeUniforms = DEFAULT_UNIFORMS;
_previousFrameTime = 0;
_redrawInterlacedStereoStencilMask = true;
_interlacedStereoStencilWidth = 0;
_interlacedStereoStencilHeight = 0;
}
@@ -950,6 +1008,136 @@ void SceneView::draw()
_renderStage->draw(*_state,previous);
}
break;
case(osg::DisplaySettings::VERTICAL_INTERLACE):
{
_localStateSet->setAttribute(_viewport.get());
// ensure that all color planes are active.
osg::ColorMask* cmask = static_cast<osg::ColorMask*>(_localStateSet->getAttribute(osg::StateAttribute::COLORMASK));
if (cmask)
{
cmask->setMask(true,true,true,true);
}
else
{
cmask = new osg::ColorMask(true,true,true,true);
_localStateSet->setAttribute(cmask);
}
_renderStageLeft->setColorMask(cmask);
_renderStageRight->setColorMask(cmask);
_renderStageLeft->drawPreRenderStages(*_state,previous);
_renderStageRight->drawPreRenderStages(*_state,previous);
glEnable(GL_STENCIL_TEST);
if(_redrawInterlacedStereoStencilMask ||
_interlacedStereoStencilWidth != _viewport->width() ||
_interlacedStereoStencilHeight != _viewport->height() )
{
_viewport->apply(*_state);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(_viewport->x(), _viewport->width(), _viewport->y(), _viewport->height(), -1.0, 1.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glDisable(GL_LIGHTING);
glDisable(GL_DEPTH_TEST);
glStencilMask(~0);
glClear(GL_STENCIL_BUFFER_BIT);
glStencilOp(GL_REPLACE, GL_REPLACE, GL_REPLACE);
glStencilFunc(GL_ALWAYS, 1, ~0);
glPolygonStipple(patternVertEven);
glEnable(GL_POLYGON_STIPPLE);
glColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
glRecti(_viewport->x(), _viewport->y(), _viewport->width(), _viewport->height());
glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
glDisable(GL_POLYGON_STIPPLE);
glEnable(GL_LIGHTING);
glEnable(GL_DEPTH_TEST);
_redrawInterlacedStereoStencilMask = false;
_interlacedStereoStencilWidth = _viewport->width();
_interlacedStereoStencilHeight = _viewport->height();
}
_renderStageLeft->setClearMask(_renderStageLeft->getClearMask() & ~(GL_STENCIL_BUFFER_BIT));
_renderStageRight->setClearMask(_renderStageRight->getClearMask() & ~(GL_STENCIL_BUFFER_BIT|GL_COLOR_BUFFER_BIT));
glStencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
glStencilFunc(GL_EQUAL, 0, ~0);
_renderStageLeft->draw(*_state,previous);
glStencilFunc(GL_NOTEQUAL, 0, ~0);
_renderStageRight->draw(*_state,previous);
glDisable(GL_STENCIL_TEST);
}
break;
case(osg::DisplaySettings::HORIZONTAL_INTERLACE):
{
_localStateSet->setAttribute(_viewport.get());
// ensure that all color planes are active.
osg::ColorMask* cmask = static_cast<osg::ColorMask*>(_localStateSet->getAttribute(osg::StateAttribute::COLORMASK));
if (cmask)
{
cmask->setMask(true,true,true,true);
}
else
{
cmask = new osg::ColorMask(true,true,true,true);
_localStateSet->setAttribute(cmask);
}
_renderStageLeft->setColorMask(cmask);
_renderStageRight->setColorMask(cmask);
_renderStageLeft->drawPreRenderStages(*_state,previous);
_renderStageRight->drawPreRenderStages(*_state,previous);
glEnable(GL_STENCIL_TEST);
if(_redrawInterlacedStereoStencilMask ||
_interlacedStereoStencilWidth != _viewport->width() ||
_interlacedStereoStencilHeight != _viewport->height() )
{
_viewport->apply(*_state);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
glOrtho(_viewport->x(), _viewport->width(), _viewport->y(), _viewport->height(), -1.0, 1.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glDisable(GL_LIGHTING);
glDisable(GL_DEPTH_TEST);
glStencilMask(~0);
glClear(GL_STENCIL_BUFFER_BIT);
glStencilOp(GL_REPLACE, GL_REPLACE, GL_REPLACE);
glStencilFunc(GL_ALWAYS, 1, ~0);
glPolygonStipple(patternHorzEven);
glEnable(GL_POLYGON_STIPPLE);
glColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
glRecti(_viewport->x(), _viewport->y(), _viewport->width(), _viewport->height());
glColorMask(GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE);
glDisable(GL_POLYGON_STIPPLE);
glEnable(GL_LIGHTING);
glEnable(GL_DEPTH_TEST);
_redrawInterlacedStereoStencilMask = false;
_interlacedStereoStencilWidth = _viewport->width();
_interlacedStereoStencilHeight = _viewport->height();
}
_renderStageLeft->setClearMask(_renderStageLeft->getClearMask() & ~(GL_STENCIL_BUFFER_BIT));
_renderStageRight->setClearMask(_renderStageRight->getClearMask() & ~(GL_STENCIL_BUFFER_BIT|GL_COLOR_BUFFER_BIT));
glStencilOp(GL_KEEP, GL_KEEP, GL_KEEP);
glStencilFunc(GL_EQUAL, 0, ~0);
_renderStageLeft->draw(*_state,previous);
glStencilFunc(GL_NOTEQUAL, 0, ~0);
_renderStageRight->draw(*_state,previous);
glDisable(GL_STENCIL_TEST);
}
break;
default:
{
osg::notify(osg::NOTICE)<<"Warning: stereo mode not implemented yet."<< std::endl;