xenoborg/alpha/source/gl_drv.c
blueshogun96@gmail.com e140504ee8
2012-01-05 00:09:50 +00:00

254 lines
No EOL
5.2 KiB
C

#include "win32.h"
#include "gl_drv.h"
/* OpenGL contexts */
HDC hdc;
HGLRC hrc;
/* Misc */
void* fb = NULL;
uint32_t fb_tex = 0;
uint32_t fb_tex_fmt = GL_BGRA_EXT;
uint32_t fb_tex_target = GL_TEXTURE_2D;
int ogl_init_fb_tex( GLsizei width, GLsizei height, GLuint target, GLenum format )
{
uint32_t* buf = NULL;
/* Delete texture if it already exists in memory */
if( fb_tex )
{
glDeleteTextures( 1, &fb_tex );
fb_tex = 0;
}
glEnable( format );
/* Create the frame buffer texture */
glGenTextures( 1, &fb_tex );
glBindTexture( target, fb_tex );
/* Initialize texture data */
/* TODO: Verify valid formats, i.e. no 24-bit, 8-bit, etc. */
fb_tex_fmt = format;
fb_tex_target = target;
glTexImage2D( target, 0, format, width, height, 0, format, GL_UNSIGNED_BYTE, fb );
/* Enable bilinear filtering */
glTexParameteri( target, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
glTexParameteri( target, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
return 1;
}
void ogl_delete_fb_tex()
{
/* Delete the frame buffer texture */
if( fb_tex )
{
glDeleteTextures( 1, &fb_tex );
fb_tex = 0;
}
}
void ogl_enable2d()
{
glMatrixMode( GL_PROJECTION );
glPushMatrix();
glLoadIdentity();
glOrtho( 0, 640, 480, 0, -1, 1 );
glMatrixMode( GL_MODELVIEW );
glPushMatrix();
glLoadIdentity();
// glTranslatef(0.375, 0.375, 0.);
glPushAttrib( GL_DEPTH_BUFFER_BIT );
glDisable( GL_DEPTH_TEST );
}
void ogl_disable2d()
{
glPopAttrib();
glMatrixMode( GL_PROJECTION );
glPopMatrix();
glMatrixMode( GL_MODELVIEW );
glPopMatrix();
}
/* Initialize OpenGL */
int enable_ogldrv( struct window_t* wnd )
{
PIXELFORMATDESCRIPTOR pfd;
int pixel_format = 0;
if( !wnd )
return 0;
/* Initialize OpenGL */
memset( &pfd, 0, sizeof(pfd) );
pfd.nVersion = 1;
pfd.cColorBits = 32;
pfd.cDepthBits = 16;
pfd.cStencilBits = 8;
pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
pfd.iPixelType = PFD_TYPE_RGBA;
pfd.iLayerType = PFD_MAIN_PLANE;
pfd.nSize = sizeof(pfd);
hdc = GetDC( wnd->hwnd );
if( !hdc )
return 0;
pixel_format = ChoosePixelFormat( hdc, &pfd );
if( !pixel_format )
return 0;
if( !SetPixelFormat( hdc, pixel_format, &pfd ) )
return 0;
hrc = wglCreateContext(hdc);
if( !hrc )
return 0;
if( !wglMakeCurrent( hdc, hrc ) )
return 0;
/* Set up viewport and projection matrix */
glViewport( 0, 0, 640, 480 );
glMatrixMode( GL_PROJECTION );
glLoadIdentity();
gluPerspective( 45.0f, 640/480, 0.1, 1000.0f );
glMatrixMode( GL_MODELVIEW );
glLoadIdentity();
/* Set up default render states */
glEnable( GL_DEPTH_TEST );
glDepthFunc( GL_LEQUAL );
glClearDepth( 1.0f );
glDisable( GL_CULL_FACE );
glDisable( GL_LIGHTING );
glDisable( GL_BLEND );
glDisable( GL_DITHER );
glDisable( GL_ALPHA_TEST );
/* Allocate framebuffer pointer */
// fb = malloc( 640*480*4 );
fb = malloc( 4*1024*1024 );
if(!fb)
return 0;
// memset( fb, 0, 640*480*4 );
memset( fb, 0, 4*1024*1024 );
/* Create framebuffer texture */
// ogl_init_fb_tex( 640, 480, GL_TEXTURE_RECTANGLE_NV, GL_BGRA_EXT );
return 1;
}
/* Uninitialize OpenGL */
void disable_ogldrv()
{
// ogl_delete_fb_tex();
if(fb)
{
free(fb);
fb = NULL;
}
if( hrc )
{
wglMakeCurrent( NULL, NULL );
wglDeleteContext( hrc );
hrc = NULL;
}
if( hdc )
{
ReleaseDC( GetActiveWindow(), hdc );
hdc = NULL;
}
}
/* Clear the colour buffer */
void ogl_clear_colour_buffer()
{
glClear( GL_COLOR_BUFFER_BIT );
}
void ogl_clear_depth_buffer()
{
glClear( GL_DEPTH_BUFFER_BIT );
}
void ogl_clear_stencil_buffer()
{
glClear( GL_STENCIL_BUFFER_BIT );
}
void ogl_swap_buffers()
{
SwapBuffers( hdc );
}
void ogl_draw_to_fb32( int x, int y, uint32_t colour )
{
unsigned char r = (colour>>16)&0xff;
unsigned char g = (colour>> 8)&0xff;
unsigned char b = (colour>> 0)&0xff;
if(!fb) return;
((unsigned int*)fb)[x+(y*640)] = (0xff<<24)|(b<<16)|(g<<8)|(r);
//((uint32_t*)fb)[x+(y*640)] = colour;
}
uint32_t ogl_read_from_fb32( int x, int y )
{
uint32_t colour = ((uint32_t*)fb)[x+(y*640)];
unsigned char b = (colour>>16)&0xff;
unsigned char g = (colour>> 8)&0xff;
unsigned char r = (colour>> 0)&0xff;
if(!fb) return 0;
return (0xff<<24)|(b<<16)|(g<<8)|(r);
}
void ogl_update_fb()
{
if(!fb) return;
#if 1
glDrawPixels( 640, 480, GL_BGRA_EXT, GL_UNSIGNED_BYTE, fb );
#else
ogl_enable2d();
glPushAttrib( GL_ALL_ATTRIB_BITS );
glEnable( fb_tex_fmt );
// glEnable( GL_BLEND );
// glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA );
glBindTexture( fb_tex_target, fb_tex );
// glTexSubImage2D( fb_tex_target, 0, 0, 0, 640, 480, fb_tex_fmt, GL_UNSIGNED_BYTE, fb );
glTexImage2D( fb_tex_target, 0, fb_tex_fmt, 640, 480, 0, fb_tex_fmt, GL_UNSIGNED_BYTE, fb );
glBegin( GL_QUADS );
glColor3f( 1.0f, 1.0f, 1.0f );
glTexCoord2f( 0.0f, 480.0f ); glVertex2f( 0, 0 );
glTexCoord2f( 640.0f, 480.0f ); glVertex2f( 640, 0 );
glTexCoord2f( 640.0f, 0.0f ); glVertex2f( 640, 480 );
glTexCoord2f( 0.0f, 0.0f ); glVertex2f( 0, 480 );
glEnd();
glPopAttrib();
ogl_disable2d();
#endif
}
void* ogl_get_fb()
{
return fb;
}