Discussion:
Cannot get projection&modelview matrix
Yanling Liu
2006-05-15 22:40:26 UTC
Permalink
Hi, My program create OpenGL context using Fox::GLCanvas, then I have a
osgUtil::SceneView to handle rendering.

Here is my code for rendering

m_sceneVeiw->update();
m_sceneView->cull();
m_scaneView->draw();

The problem is I cannot get OpenGL projection and modelview matrix using
glGetDoublev(...). All I got is identity matrix for both projection and
modelview.

So the questions are:
1. does osg has any special process/locking about OpenGL projection and
modelview matrix?
2. Is that safe to use camera projection and modelview matrix of
osgUtil::SceneView when I need to use OpenGL projection and modelview
matrix?

Yanling
Yanling Liu
2006-05-16 17:49:07 UTC
Permalink
Hi Janling,
Post by Yanling Liu
Hi, My program create OpenGL context using Fox::GLCanvas, then I have a
osgUtil::SceneView to handle rendering.
Here is my code for rendering
m_sceneVeiw->update();
m_sceneView->cull();
m_scaneView->draw();
The problem is I cannot get OpenGL projection and modelview matrix using
glGetDoublev(...). All I got is identity matrix for both projection and
modelview.
You can only use glGet* methods from within the current context. Also the
OSG itself manages the projection and model view matrices so these values
will change throught the draw traversal.
I am not quite sure when you are saying the current context. Are you talking
about osg's current context or OpenGL's context? I am sure I have used
glGet* methods in the current OpenGL context. Also I have tried to use
glGet* in osgHud examples like this:

while( !viewer.done() )
{
// wait for all cull and draw threads to complete.
viewer.sync();

// update the scene by traversing it with the the update visitor
which will
// call all node update callbacks and animations.
viewer.update();

double proj[16];
glGetDoublev(GL_PROJECTION_MATRIX, proj);
//after get I output the projection matrix using std::cout
//std::cout<<proj[0]<<" "<<proj[1]<<" ".....

// fire off the cull and draw traversals of the scene.
viewer.frame();

}

Still I can only get identical projection matrix. Don't know how to make
sure current context in such situation.
Post by Yanling Liu
1. does osg has any special process/locking about OpenGL projection and
modelview matrix?
No, but OpenGL is state machine, you'll only ever be abe to get the last
values applied to OpenGL using glGet methods, and you can only do it from a
valid graphics context. As a general note, avoid using glGets in OpenGL
application, as it can stall the whole graphics pipeline and kill
performance.
2. Is that safe to use camera projection and modelview matrix of
Post by Yanling Liu
osgUtil::SceneView when I need to use OpenGL projection and modelview
matrix?
When and why do you need the projection and modelview matrices?
If you need them from the draw traversal then look no further than the
osg::State object passed into each Drawable::drawImplementation(State&) and
the osg::State object has getProjectionMatrix and getModelViewMatrix()
methods, these just return locally cached OSG matrices, and don't require
any glGet* which is a boon for convinience and performance.
I need to integrate haptic device and Sharp 3D stereo display into my
project. Both of them require OpenGL projection matrix to initialize and
update themselve during rendering. You could see this in following code:

void CCAuxFoxGLWindow::Render(void)
{
osg::Timer_t startTick = osg::Timer::instance()->tick();

if (m_isScannerEnable)
m_pScannerBar->DoRTS();

//here I need to update haptic device workspace using OpenGL proj
matrix.
//code of UpdateCurrentToolOriPos() is at below
if (m_isHapticUsed)
UpdateCurrentToolOriPos();

//m_sceneView is extended from osgUtil::SceneView
m_sceneView->PerformVirtualSurgery();
m_sceneView->UpdateScene();//do update() and cull()

if (m_isHapticUsed)
{
hlBeginFrame();
m_sceneView->draw();
hlEndFrame();
}
else
m_sceneView->draw();

//post processing
if (m_isFrameColorBoost)
FrameColorBoost();

if (m_isSnapShot)
Snapshot();

if (m_isRecordMovie)
RecordMovie();

m_pGLCanvas->swapBuffers();
osg::Timer_t endTick = osg::Timer::instance()->tick();
m_sceneView->UpdateFPS(osg::Timer::instance()->delta_s(startTick,
endTick));
}

// update current tool's orientation and position
void CCAuxFoxGLWindow::UpdateCurrentToolOriPos(void)
{
GLdouble projection[16];
hlMatrixMode(HL_TOUCHWORKSPACE);
hlLoadIdentity();

glGetDoublev(GL_PROJECTION_MATRIX, projection);
// I tried to use camera projection matrix, but still have problem
//
hluFitWorkspace(m_sceneView->getCamera()->getProjectionMatrix().ptr());
hluFitWorkspace(projection);

double position[3];
double rotation[4];

hlGetDoublev(HL_DEVICE_POSITION, position);
hlGetDoublev(HL_DEVICE_ROTATION, rotation);

osg::Vec3f pos(position[0], -position[2], position[1]);
osg::Quat ori(rotation[0], rotation[1], rotation[2], rotation[3]);

m_sceneView->GetVSToolGroup()->TransformCurrentTool(pos, ori);
}


Yanling


Robert.
_______________________________________________
osg-users mailing list
http://openscenegraph.net/mailman/listinfo/osg-users
http://www.openscenegraph.org/
Robert Osfield
2006-05-16 18:39:17 UTC
Permalink
HI Yanling,

I am not quite sure when you are saying the current context. Are you talking
Post by Yanling Liu
about osg's current context or OpenGL's context? I am sure I have used
glGet* methods in the current OpenGL context. Also I have tried to use
while( !viewer.done() )
{
// wait for all cull and draw threads to complete.
viewer.sync();
// update the scene by traversing it with the the update visitor
which will
// call all node update callbacks and animations.
viewer.update();
double proj[16];
glGetDoublev(GL_PROJECTION_MATRIX, proj);
//after get I output the projection matrix using std::cout
//std::cout<<proj[0]<<" "<<proj[1]<<" ".....
// fire off the cull and draw traversals of the scene.
viewer.frame();
}
The glGetDouble is not in thread that has the current graphics context as
will produce undefined results if not a crash...

Use the Viewer's (subclassed from Producer::CameraGroup) setLens/getLens and
getViewMatrix.

Robert.
Yanling Liu
2006-05-16 22:50:23 UTC
Permalink
Post by Robert Osfield
HI Yanling,
I am not quite sure when you are saying the current context. Are you
talking about osg's current context or OpenGL's context? I am sure I have
used glGet* methods in the current OpenGL context. Also I have tried to use
while( !viewer.done() )
{
// wait for all cull and draw threads to complete.
viewer.sync();
// update the scene by traversing it with the the update visitor
which will
// call all node update callbacks and animations.
viewer.update();
double proj[16];
glGetDoublev(GL_PROJECTION_MATRIX, proj);
//after get I output the projection matrix using std::cout
//std::cout<<proj[0]<<" "<<proj[1]<<" ".....
// fire off the cull and draw traversals of the scene.
viewer.frame();
}
The glGetDouble is not in thread that has the current graphics context as
will produce undefined results if not a crash...
Use the Viewer's (subclassed from Producer::CameraGroup) setLens/getLens
and getViewMatrix.
Could I use osgUtil::SceneView's getProjectionMatrix as the substitution for
glGet*?

Robert.
Post by Robert Osfield
_______________________________________________
osg-users mailing list
http://openscenegraph.net/mailman/listinfo/osg-users
http://www.openscenegraph.org/
Yanling Liu
2006-05-16 23:13:54 UTC
Permalink
Thanks Robert.

You said that "The glGetDouble is not in thread that has the current
graphics context as will produce undefined results if not a crash..."

But which thread actually has the current graphics context? I see that my
program has only one thread in Windows task manager. I created the opengl
context in the only thread but later on the thread could not have the
current context? Does OSG induce some hidden threads which take over the
current context from my thread?

Yanling
Post by Robert Osfield
HI Yanling,
I am not quite sure when you are saying the current context. Are you
talking about osg's current context or OpenGL's context? I am sure I have
used glGet* methods in the current OpenGL context. Also I have tried to use
while( !viewer.done() )
{
// wait for all cull and draw threads to complete.
viewer.sync();
// update the scene by traversing it with the the update visitor
which will
// call all node update callbacks and animations.
viewer.update();
double proj[16];
glGetDoublev(GL_PROJECTION_MATRIX, proj);
//after get I output the projection matrix using std::cout
//std::cout<<proj[0]<<" "<<proj[1]<<" ".....
// fire off the cull and draw traversals of the scene.
viewer.frame();
}
The glGetDouble is not in thread that has the current graphics context as
will produce undefined results if not a crash...
Use the Viewer's (subclassed from Producer::CameraGroup) setLens/getLens
and getViewMatrix.
Robert.
_______________________________________________
osg-users mailing list
http://openscenegraph.net/mailman/listinfo/osg-users
http://www.openscenegraph.org/
Robert Osfield
2006-05-17 07:39:13 UTC
Permalink
Post by Yanling Liu
Thanks Robert.
You said that "The glGetDouble is not in thread that has the current
graphics context as will produce undefined results if not a crash..."
But which thread actually has the current graphics context? I see that my
program has only one thread in Windows task manager. I created the opengl
context in the only thread but later on the thread could not have the
current context? Does OSG induce some hidden threads which take over the
current context from my thread?
Producer can thread the frame method, one thread per camera. If you have
just one camera then it'll be single threaded, but if you have two cameras
then it'll select multi-threaded.

If you are using a Producer based viewer such as osgProducer::Viewer then
please use the Producer::CameraGroup for view and projection matrices - the
projection matrices under the lens controls.

Robert.
Yanling Liu
2006-05-17 23:11:45 UTC
Permalink
I did not use Producer based viewer at all. I used an osgUtil::sceneView
with single camera. That's why I feel weird about getting identity
projection matrix.

The reason for me to use sceneView instead of osgProducer::Viewer is because
I need traditional 2D GUI such as menus, dialog, option windows in my
program. You could see it form this image
Loading Image.... No idea how to
integrate those things into osgProducer::Viewer.

Yanling
Post by Robert Osfield
Post by Yanling Liu
Thanks Robert.
You said that "The glGetDouble is not in thread that has the current
graphics context as will produce undefined results if not a crash..."
But which thread actually has the current graphics context? I see that
my program has only one thread in Windows task manager. I created the opengl
context in the only thread but later on the thread could not have the
current context? Does OSG induce some hidden threads which take over the
current context from my thread?
Producer can thread the frame method, one thread per camera. If you have
just one camera then it'll be single threaded, but if you have two cameras
then it'll select multi-threaded.
If you are using a Producer based viewer such as osgProducer::Viewer then
please use the Producer::CameraGroup for view and projection matrices - the
projection matrices under the lens controls.
Robert.
_______________________________________________
osg-users mailing list
http://openscenegraph.net/mailman/listinfo/osg-users
http://www.openscenegraph.org/
Robert Osfield
2006-05-18 08:02:11 UTC
Permalink
Post by Yanling Liu
I did not use Producer based viewer at all. I used an osgUtil::sceneView
with single camera. That's why I feel weird about getting identity
projection matrix.
The reason for me to use sceneView instead of osgProducer::Viewer is
because I need traditional 2D GUI such as menus, dialog, option windows in
my program. You could see it form this image
Loading Image...>.
No idea how to integrate those things into osgProducer::Viewer.
Have you see the osghud example? This provides and example of putting up
2D data as part of your main scene graph.

Others have also integrated GUI toolkits with he OSG, such as GLGoey, so
have a search through the community section of the website.

And finally use SceneView->getProjectionMatrix()/getViewMatrix() over the
OpenGL gets.

Robert.
#POH CHENG GUAN#
2006-05-18 08:51:30 UTC
Permalink
Hi,

I've created 2 camera manipulators. When I switch to camera A and back to camera B, the view is different from the last seen camera B's view. How do I maintain the last seen view when switching between cameras?

Regards,
Tim

Loading...