Search
lxdream.org :: lxdream/src/drivers/gl_common.c :: diff
lxdream 0.9.1
released Jun 29
Download Now
filename src/drivers/gl_common.c
changeset 352:f0df7a6d4703
next424:421d68e78c46
author nkeynes
date Sun Feb 11 10:09:32 2007 +0000 (12 years ago)
permissions -rw-r--r--
last change Bug 27: Implement opengl framebuffer objects
Rewrite much of the final video output stage. Now uses generic "render
buffers", implemented on GL using framebuffer objects + textures.
file annotate diff log raw
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/src/drivers/gl_common.c Sun Feb 11 10:09:32 2007 +0000
1.3 @@ -0,0 +1,160 @@
1.4 +/**
1.5 + * $Id: gl_common.c,v 1.1 2007-02-11 10:09:32 nkeynes Exp $
1.6 + *
1.7 + * Common GL code that doesn't depend on a specific implementation
1.8 + *
1.9 + * Copyright (c) 2005 Nathan Keynes.
1.10 + *
1.11 + * This program is free software; you can redistribute it and/or modify
1.12 + * it under the terms of the GNU General Public License as published by
1.13 + * the Free Software Foundation; either version 2 of the License, or
1.14 + * (at your option) any later version.
1.15 + *
1.16 + * This program is distributed in the hope that it will be useful,
1.17 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
1.18 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
1.19 + * GNU General Public License for more details.
1.20 + */
1.21 +
1.22 +#include <GL/gl.h>
1.23 +#include "dream.h"
1.24 +#include "drivers/gl_common.h"
1.25 +
1.26 +extern uint32_t video_width, video_height;
1.27 +
1.28 +char *required_extensions[] = { "GL_EXT_framebuffer_object", NULL };
1.29 +
1.30 +/**
1.31 + * Test if a specific extension is supported. From opengl.org
1.32 + * @param extension extension name to check for
1.33 + * @return TRUE if supported, otherwise FALSE.
1.34 + */
1.35 +gboolean isGLExtensionSupported( const char *extension )
1.36 +{
1.37 + const GLubyte *extensions = NULL;
1.38 + const GLubyte *start;
1.39 + GLubyte *where, *terminator;
1.40 +
1.41 + /* Extension names should not have spaces. */
1.42 + where = (GLubyte *) strchr(extension, ' ');
1.43 + if (where || *extension == '\0')
1.44 + return 0;
1.45 + extensions = glGetString(GL_EXTENSIONS);
1.46 + /* It takes a bit of care to be fool-proof about parsing the
1.47 + OpenGL extensions string. Don't be fooled by sub-strings,
1.48 + etc. */
1.49 + start = extensions;
1.50 + for (;;) {
1.51 + where = (GLubyte *) strstr((const char *) start, extension);
1.52 + if (!where)
1.53 + break;
1.54 + terminator = where + strlen(extension);
1.55 + if (where == start || *(where - 1) == ' ')
1.56 + if (*terminator == ' ' || *terminator == '\0')
1.57 + return TRUE;
1.58 + start = terminator;
1.59 + }
1.60 + return FALSE;
1.61 +}
1.62 +
1.63 +gboolean hasRequiredGLExtensions( )
1.64 +{
1.65 + int i;
1.66 + gboolean isOK = TRUE;
1.67 +
1.68 + for( i=0; required_extensions[i] != NULL; i++ ) {
1.69 + if( !isGLExtensionSupported(required_extensions[i]) ) {
1.70 + ERROR( "Required OpenGL extension not supported: %s", required_extensions[i] );
1.71 + isOK = FALSE;
1.72 + }
1.73 + }
1.74 + return isOK;
1.75 +}
1.76 +
1.77 +
1.78 +gboolean gl_display_frame_buffer( frame_buffer_t frame )
1.79 +{
1.80 + GLenum type = colour_formats[frame->colour_format].type;
1.81 + GLenum format = colour_formats[frame->colour_format].format;
1.82 + int bpp = colour_formats[frame->colour_format].bpp;
1.83 + GLint texid;
1.84 +
1.85 + glViewport( 0, 0, video_width, video_height );
1.86 + glMatrixMode(GL_PROJECTION);
1.87 + glLoadIdentity();
1.88 + glOrtho( 0, video_width, video_height, 0, 0, -65535 );
1.89 + glMatrixMode(GL_MODELVIEW);
1.90 + glLoadIdentity();
1.91 +
1.92 + /* Disable everything */
1.93 + glDisable( GL_TEXTURE_2D );
1.94 + glDisable( GL_ALPHA_TEST );
1.95 + glDisable( GL_DEPTH_TEST );
1.96 + glDisable( GL_SCISSOR_TEST );
1.97 + glDisable( GL_CULL_FACE );
1.98 +
1.99 + float scale = ((float)video_height) / frame->height;
1.100 + int rowstride = (frame->rowstride / bpp) - frame->width;
1.101 +
1.102 +
1.103 + /*
1.104 + glGenTextures( 1, &texid );
1.105 + glBindTexture( GL_TEXTURE_2D, texid );
1.106 + glTexImage2D( GL_TEXTURE_2D, 0, colour_formats[frame->colour_format].int_format,
1.107 + frame->width, frame->height, 0, format, type, frame->data );
1.108 + glBegin( GL_QUADS );
1.109 + glTexCoord2i( 0, 1.0 );
1.110 + glVertex2f( 0.0, 0.0 );
1.111 + glTexCoord2i( 1.0, 1.0 );
1.112 + glVertex2f( frame->width, 0.0 );
1.113 + glTexCoord2i( 1.0, 0.0 );
1.114 + glVertex2f( frame->width, frame->height );
1.115 + glTexCoord2i( 0, 0.0 );
1.116 + glVertex2f( 0.0, frame->height );
1.117 + glEnd();
1.118 + glDeleteTextures( 1, &texid );
1.119 + */
1.120 + glRasterPos2i( 0, 0 );
1.121 + glPixelZoom( 1.0f, -scale );
1.122 + glPixelStorei( GL_UNPACK_ROW_LENGTH, rowstride );
1.123 + glDrawPixels( frame->width, frame->height, format, type,
1.124 + frame->data );
1.125 +
1.126 + glFlush();
1.127 + return TRUE;
1.128 +}
1.129 +
1.130 +gboolean gl_display_blank( uint32_t colour )
1.131 +{
1.132 + glViewport( 0, 0, video_width, video_height );
1.133 + glMatrixMode( GL_PROJECTION );
1.134 + glLoadIdentity();
1.135 + glOrtho( 0, video_width, video_height, 0, 0, -65535 );
1.136 + glMatrixMode(GL_MODELVIEW);
1.137 + glLoadIdentity();
1.138 + glColor3b( (colour >> 16) & 0xFF, (colour >> 8) & 0xFF, colour & 0xFF );
1.139 + glRecti(0,0, video_width, video_height );
1.140 + glFlush();
1.141 + return TRUE;
1.142 +}
1.143 +
1.144 +/**
1.145 + * Generic GL read_render_buffer. This function assumes that the caller
1.146 + * has already set the appropriate glReadBuffer(); in other words, unless
1.147 + * there's only one buffer this needs to be wrapped.
1.148 + */
1.149 +gboolean gl_read_render_buffer( render_buffer_t buffer, char *target )
1.150 +{
1.151 + if( buffer->address == -1 )
1.152 + return FALSE;
1.153 + glFinish();
1.154 + GLenum type = colour_formats[buffer->colour_format].type;
1.155 + GLenum format = colour_formats[buffer->colour_format].format;
1.156 + int line_size = buffer->width * colour_formats[buffer->colour_format].bpp;
1.157 + int size = line_size * buffer->height;
1.158 + int rowstride = (buffer->rowstride / colour_formats[buffer->colour_format].bpp) - buffer->width;
1.159 + // glPixelStorei( GL_PACK_ROW_LENGTH, rowstride );
1.160 +
1.161 + glReadPixels( 0, 0, buffer->width, buffer->height, format, type, target );
1.162 + return TRUE;
1.163 +}
.