Flat functions |
TestRC | void TestRC(HWND hWnd, HDC * hDC,HGLRC *hRC) |
GetCurrentQGLContext | QGLContext *GetCurrentQGLContext() |
SetCurrentQGLContext | void SetCurrentQGLContext(QGLContext *glc) Expert function to influence the current GLContext |
class QGLContext | .h |
constructor | QGLContext(QXWindow *iwin,XVisualInfo *vi,QGLContext *share, bool direct) |
Flat functions |
GetHD">sprintf(buf,"QGLCtx: iwin=%p, hdc=%p, hRC=%p",iwin,iwin->GetHD | sprintf(buf,"QGLCtx: iwin=%p, hdc=%p, hRC=%p",iwin,iwin->GetHDC(),hRC); MessageBox(0,buf,"QGLContext ctor",MB_OK); HDC hDC=iwin->GetHDC(); Select(); Select(); Select(); estRC(iwin->GetHWND(),&hDC,&hRC); */ //wglMakeCurrent(hDC, *hRC ); #else if(share)shctx=share->ctx; else shctx=0; ctx=glXCreateContext(XDSP,vi,shctx,direct); #endif } QGLContext::QGLContext(GLXContext _ctx) Create from existing context |
class QGLContext | .h |
destructor | ~QGLContext() |
GetGLXContext | GLXContext GetGLXContext() |
SetWindow | void SetWindow(QXWindow *nwin) |
SetDrawable | void SetDrawable(QDrawable *draw) Sets drawable to paint on |
Select | void Select(QDrawable *draw,QDrawable *read) Uses this context as the current context for this thread |
Flat functions |
GetHD">sprintf(buf,"xw=%p, hdc=%p, hRC=%p",xw,xw->GetHD | sprintf(buf,"xw=%p, hdc=%p, hRC=%p",xw,xw->GetHDC(),hRC); MessageBox(0,buf,"trace",MB_OK);*/ if(xw) { log(QLOG_INFO,"QGLContext:Select: hdc=%p, hrc=%p",xw->GetHDC(),hRC); wglMakeCurrent(xw->GetHDC(),hRC); #ifdef OBS // Test glClearColor(.4,.5,.6,1); glClear(GL_COLOR_BUFFER_BIT); #endif } else qerr("QGLContext:Select(); drawable doesn't seem to be a QXWindow"); #else //glXMakeCurrent(app->GetDisplay()->GetXDisplay(),win->GetXWindow(),ctx); if(drawableRead==0) { glXMakeCurrent(XDSP,drawable->GetGLXDrawable(),ctx); } else { // Use both DRAW & READ glXMakeCurrentReadSGI(XDSP,draw->GetGLXDrawable(),read->GetGLXDrawable(), ctx); } #endif curglc=this; //qdbg("QGLCtx:Select RET\n"); } void QGLContext::Swap() |
class QGLContext | .h |
Setup2DWindow | void Setup2DWindow() Use defaults settings to provide a parallel view in 2D |
Setup3DWindow | void Setup3DWindow(int dist) Generate default 3D view, camera at z=-$dist results in pixel-pixel mapping |
Viewport | void Viewport(int x,int y,int wid,int hgt) |
DrawBuffer | void DrawBuffer(int d) |
ReadBuffer | void ReadBuffer(int d) |
Clear | void Clear(int buffers) |
MatrixMode | void MatrixMode(int m) |
LoadIdentity | void LoadIdentity() |
Ortho | void Ortho(qdouble l,qdouble r,qdouble t,qdouble b, qdouble n,qdouble f) Left/right/top/bottom/near/far |
Disable | void Disable(int n) |
Enable | void Enable(int n) |
BlendFunc | void BlendFunc(int sf,int df) |
/*
* QOpenGL - wrapper around OpenGL / GLX contexts / WGL
* 28-04-97: Created!
* 03-03-98: Bug removed; if a context was created, then deleted, it might
* still be cached as current (in curglc), which could lead to spurious
* problems when a following new Context resulted in the same pointer value!
* 28-02-99: Major revisions in class hierarchy; QDrawable etc.
* 27-07-00: Win32 WGL support. A bit woven here & there.
* (C) MarketGraph/RVG
*/
#include <qlib/opengl.h>
#include <qlib/app.h>
#include <qlib/display.h>
#ifdef WIN32
#include <windows.h>
#include <GL/gl.h>
#endif
#include <GL/glx.h>
#include <qlib/debug.h>
DEBUG_ENABLE
// Shortcut for context selection
#define SEL if(curglc!=this)Select()
// Global current GL context for fast context switching checks
static QGLContext *curglc;
#ifdef ND_TEST_WIN32_GLRC
void TestRC(HWND hWnd, HDC * hDC,HGLRC *hRC)
{ int i;
//*hRC=wglCreateContext(*hDC);
//wglMakeCurrent(*hDC,*hRC);
glClearColor( 0.2f, 0.5f, 0.3f, 0.0f );
glClear( GL_COLOR_BUFFER_BIT );
glPushMatrix();
glRotatef( 25.0f, 0.0f, 0.0f, 1.0f );
glBegin( GL_TRIANGLES );
glColor3f( 1.0f, 0.0f, 0.0f ); glVertex2f( 0.0f, 1.0f );
glColor3f( 0.0f, 1.0f, 0.0f ); glVertex2f( 0.87f, -0.5f );
glColor3f( 0.0f, 0.0f, 1.0f ); glVertex2f( -0.87f, -0.5f );
glEnd();
glPopMatrix();
SwapBuffers(*hDC);
glFlush();
for(i=0;i<100000000;i++);
glFinish();
for(i=0;i<100000000;i++);
SwapBuffers(hDC);
for(i=0;i<100000000;i++);
glFinish();
for(i=0;i<100000000;i++);
}
#endif
// Global functions
QGLContext *GetCurrentQGLContext()
{ return curglc;
}
void SetCurrentQGLContext(QGLContext *glc)
// Expert function to influence the current GLContext
{ curglc=glc;
}
QGLContext::QGLContext(QXWindow *iwin,XVisualInfo *vi,QGLContext *share,
QGLContext::QGLContext(QXWindow *iwin,XVisualInfo *vi,QGLContext *share, bool direct)
{
GLXContext shctx;
//qdbg("***** QGLCtx ctor %p\n",this);
//internal=(QGLContextInternal*)qcalloc(sizeof(*internal));
flags=0;
ctx=0;
//win=iwin;
drawable=iwin;
drawableRead=iwin;
#ifdef WIN32
// Create WGL context
//qerr("QGLContext ctor nyi/win32");
// create the render context (RC)
hRC=wglCreateContext(iwin->GetHDC());
// Share display lists
if(share)
wglShareLists(share->GetHRC(),hRC);
/*
char buf[80];
GetHD">sprintf(buf,"QGLCtx: iwin=%p, hdc=%p, hRC=%p",iwin,iwin->GetHDC(),hRC);
MessageBox(0,buf,"QGLContext ctor",MB_OK);
HDC hDC=iwin->GetHDC();
Select(); Select(); Select();
//TestRC(iwin->GetHWND(),&hDC,&hRC);
*/
//wglMakeCurrent(hDC, *hRC );
#else
if(share)shctx=share->ctx;
else shctx=0;
ctx=glXCreateContext(XDSP,vi,shctx,direct);
#endif
}
QGLContext::QGLContext(GLXContext _ctx)
// Create from existing context
{
#ifdef WIN32
qerr("QGLContext ctor(GLXContext ctx) nyi/win32");
#endif
flags=F_USER_CTX;
ctx=_ctx;
drawable=0;
drawableRead=0;
}
QGLContext::~QGLContext()
{ //qdbg("***** QGLCtx dtor %p\n",this);
//if(internal->glxContext)
// Destroy context if we own it
#ifdef WIN32
//qerr("QGLContext dtor nyi/win32");
#else
// GLX
if(ctx!=0&&((flags&F_USER_CTX)==0))
glXDestroyContext(XDSP,ctx);
#endif
//if(internal)qfree(internal);
// 3-3-98; Cancel this context if it is active!!
if(curglc==this)
curglc=0;
}
GLXContext QGLContext::GetGLXContext()
{ return ctx; // internal->glxContext;
}
#ifdef OBS
void QGLContext::SetWindow(QXWindow *nwin)
{ win=nwin;
}
// GetWindow is inline
#endif
void QGLContext::SetDrawable(QDrawable *draw)
// Sets drawable to paint on
{
drawable=draw;
}
//void QGLContext::Select(QXWindow *nwin)
void QGLContext::Select(QDrawable *draw,QDrawable *read)
// Uses this context as the current context for this thread
{
// Cached
if(curglc==this)return;
//qdbg("QGLCtx:Select; this=%p, draw=%p\n",this,draw);
if(draw)drawable=draw;
drawableRead=read;
#ifdef WIN32
// Make current
QXWindow *xw;
//xw=dynamic_cast<QXWindow*>(drawable);
xw=(QXWindow*)drawable;
/*char buf[128];
GetHD">sprintf(buf,"xw=%p, hdc=%p, hRC=%p",xw,xw->GetHDC(),hRC);
MessageBox(0,buf,"trace",MB_OK);*/
if(xw)
{
//qlog(QLOG_INFO,"QGLContext:Select: hdc=%p, hrc=%p",xw->GetHDC(),hRC);
wglMakeCurrent(xw->GetHDC(),hRC);
#ifdef OBS
// Test
glClearColor(.4,.5,.6,1);
glClear(GL_COLOR_BUFFER_BIT);
#endif
}
else qerr("QGLContext:Select(); drawable doesn't seem to be a QXWindow");
#else
//glXMakeCurrent(app->GetDisplay()->GetXDisplay(),win->GetXWindow(),ctx);
if(drawableRead==0)
{ glXMakeCurrent(XDSP,drawable->GetGLXDrawable(),ctx);
} else
{ // Use both DRAW & READ
glXMakeCurrentReadSGI(XDSP,draw->GetGLXDrawable(),read->GetGLXDrawable(),
ctx);
}
#endif
curglc=this;
//qdbg("QGLCtx:Select RET\n");
}
void QGLContext::Swap()
{
SEL;
#ifdef WIN32
QXWindow *xw;
xw=(QXWindow*)drawable;
if(xw)SwapBuffers(xw->GetHDC());
#else
// GLX
glXSwapBuffers(XDSP,drawable->GetGLXDrawable());
#endif
}
/*****************
* WINDOW SUPPORT *
*****************/
void QGLContext::Setup2DWindow()
// Use defaults settings to provide a parallel view in 2D
{ int wid,hgt;
QASSERT_V(drawable);
SEL;
//qdbg("QGLContext:Setup2DWindow\n");
//qdbg(" xw=%x, win=%p\n",win->GetXWindow(),win);
wid=drawable->GetWidth();
hgt=drawable->GetHeight();
//qdbg(" drawable %p = %dx%d\n",drawable,wid,hgt);
//qdbg(" vp\n");
Viewport(0,0,wid,hgt);
MatrixMode(GL_PROJECTION);
LoadIdentity();
MatrixMode(GL_MODELVIEW);
LoadIdentity();
//qdbg(" ortho\n");
Ortho(0,(qdouble)wid,0,(qdouble)hgt,-1,1);
//qdbg("QGLContext:Setup2DWindow() RET\n");
}
void QGLContext::Setup3DWindow(int dist)
// Generate default 3D view, camera at z=-$dist results in pixel-pixel mapping
{
int wid,hgt;
GLfloat idDistance;
QASSERT_V(drawable);
SEL;
idDistance=dist; // Convert to float
wid=drawable->GetWidth();
hgt=drawable->GetHeight();
//qdbg("QGLCtx:3D: %dx%d drawable\n",wid,hgt);
//QShowGLErrors("QGLCtx:1");
// 3D view
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
//QShowGLErrors("QGLCtx:2");
//GLfloat idDistance=1000; // Distance (Z) to fully cover window
//gluPerspective(60,(GLfloat)720/(GLfloat)576,0.1,1000);
glFrustum(-wid/idDistance/2,wid/idDistance/2,
-hgt/idDistance/2,hgt/idDistance/2, 1,100000);
//QShowGLErrors("QGLCtx:3");
glMatrixMode(GL_MODELVIEW);
//QShowGLErrors("QGLCtx:4");
glLoadIdentity();
// Setup camera distance; objects at this distance map 1:1 on the drawable
glTranslatef(0,0,-idDistance);
//QShowGLErrors("QGLCtx:5");
}
/*********
* OPENGL *
*********/
void QGLContext::Viewport(int x,int y,int wid,int hgt)
{
//qdbg("QGLCtx:Viewport()\n");
//qdbg(" curglc=%p, this=%p\n",curglc,this);
SEL;
//qdbg(" vprt\n");
glViewport(x,y,wid,hgt);
//qdbg("QGLCtx:Viewport() RET\n");
}
void QGLContext::DrawBuffer(int d)
{ SEL;
//printf("GLC:DrawBuffer %d ctx %p\n",d,glXGetCurrentContext());
glDrawBuffer(d);
}
void QGLContext::ReadBuffer(int d)
{ SEL;
//printf("GLC:ReadBuffer %d ctx %p\n",d,glXGetCurrentContext());
glReadBuffer(d);
}
void QGLContext::Clear(int buffers)
{ SEL;
glClear(buffers);
}
void QGLContext::MatrixMode(int m)
{ SEL;
glMatrixMode(m);
}
void QGLContext::LoadIdentity()
{ SEL;
glLoadIdentity();
}
void QGLContext::Ortho(qdouble l,qdouble r,qdouble t,qdouble b,
void QGLContext::Ortho(qdouble l,qdouble r,qdouble t,qdouble b, qdouble n,qdouble f)
// Left/right/top/bottom/near/far
{ SEL;
glOrtho(l,r,t,b,n,f);
}
void QGLContext::Disable(int n)
{ SEL;
glDisable(n);
}
void QGLContext::Enable(int n)
{ SEL;
glEnable(n);
}
void QGLContext::BlendFunc(int sf,int df)
{ SEL;
glBlendFunc(sf,df);
}