Merge branch 'sdl_android' of github.com:pelya/commandergenius into sdl_android

This commit is contained in:
Sergii Pylypenko
2015-10-01 22:47:04 +03:00
21 changed files with 499 additions and 339 deletions

View File

@@ -7,10 +7,10 @@ AppName="Commander Genius"
AppFullName=net.sourceforge.clonekeenplus AppFullName=net.sourceforge.clonekeenplus
# Application version code (integer) # Application version code (integer)
AppVersionCode=182210 AppVersionCode=182300
# Application user-visible version name (string) # Application user-visible version name (string)
AppVersionName="1.8.2.2-1 Release" AppVersionName="1.8.3.0 Release"
# Specify path to download application data in zip archive in the form 'Description|URL|MirrorURL^Description2|URL2|MirrorURL2^...' # Specify path to download application data in zip archive in the form 'Description|URL|MirrorURL^Description2|URL2|MirrorURL2^...'
# If you'll start Description with '!' symbol it will be enabled by default, other downloads should be selected by user from startup config menu # If you'll start Description with '!' symbol it will be enabled by default, other downloads should be selected by user from startup config menu
@@ -18,7 +18,7 @@ AppVersionName="1.8.2.2-1 Release"
# If the URL does not contain 'http://' it is treated as file from 'project/jni/application/src/AndroidData' dir - # If the URL does not contain 'http://' it is treated as file from 'project/jni/application/src/AndroidData' dir -
# these files are put inside .apk package by build system # these files are put inside .apk package by build system
# Also please avoid 'https://' URLs, many Android devices do not have trust certificates and will fail to connect to SF.net over HTTPS # Also please avoid 'https://' URLs, many Android devices do not have trust certificates and will fail to connect to SF.net over HTTPS
AppDataDownloadUrl="!Keen1|keen1.zip^!Keen4|keen4.zip^!Keen7|keen7.zip^High-quality GFX and music - 55 Mb|http://sourceforge.net/projects/clonekeenplus/files/High%20Quality%20Packs/Version%202.x/hqpv26.zip/download" AppDataDownloadUrl="!Keen1|keen1.zip^!Keen4|keen4.zip^!Keen7|keen7.zip^!Accumulators|Accumulators.zip^High-quality GFX and music - 55 Mb|http://sourceforge.net/projects/clonekeenplus/files/High%20Quality%20Packs/Version%202.x/hqpv26.zip/download"
# Reset SDL config when updating application to the new version (y) / (n) # Reset SDL config when updating application to the new version (y) / (n)
ResetSdlConfigForThisVersion=y ResetSdlConfigForThisVersion=y

View File

@@ -1,4 +1,5 @@
#include "array.h" #include "array.h"
#include "debug.h"
GLvoid *copy_gl_array(const GLvoid *src, GLvoid *copy_gl_array(const GLvoid *src,
GLenum from, GLsizei width, GLsizei stride, GLenum from, GLsizei width, GLsizei stride,
@@ -63,16 +64,51 @@ GLvoid *copy_gl_array(const GLvoid *src,
return dst; return dst;
} }
GLvoid *copy_gl_array_quickconvert(const GLvoid *src,
GLenum from, GLsizei stride,
GLsizei skip, GLsizei count) {
if (! stride)
stride = 4 * gl_sizeof(from);
const char *unknown_str = "libGL: copy_gl_array_quickconvert -> unknown type: %x\n";
GLvoid *dst = malloc((count-skip) * 4 * gl_sizeof(GL_FLOAT));
GLsizei from_size = gl_sizeof(from) * 4;
GLsizei to_size = gl_sizeof(GL_FLOAT) * 4;
uintptr_t in = (uintptr_t)src;
in += stride*skip;
int j;
GLfloat *out = (GLfloat*)dst;
GL_TYPE_SWITCH2(input, in, from,
const GLfloat maxf = 1.0f/gl_max_value(from);
for (int i = skip; i < count; i++)
,
for (j = 0; j < 4; j++) {
out[j] = ((GLfloat)input[j])*maxf;
}
out += 4;
in += stride;
,
default:
printf(unknown_str, from);
return NULL;
)
return dst;
}
GLvoid *copy_gl_array_convert(const GLvoid *src, GLvoid *copy_gl_array_convert(const GLvoid *src,
GLenum from, GLsizei width, GLsizei stride, GLenum from, GLsizei width, GLsizei stride,
GLenum to, GLsizei to_width, GLsizei skip, GLsizei count, GLvoid* filler) { GLenum to, GLsizei to_width, GLsizei skip, GLsizei count, GLvoid* filler) {
if (! src || !count) if (! src || !count)
return NULL; return NULL;
if(to==GL_FLOAT && width==to_width && width==4)
return copy_gl_array_quickconvert(src, from, stride, skip, count);
if (! stride) if (! stride)
stride = width * gl_sizeof(from); stride = width * gl_sizeof(from);
const char *unknown_str = "libGL: copy_gl_array_convert -> unknown type: %x\n";
const char *unknown_str = "libGL: copy_gl_array -> unknown type: %x\n";
GLvoid *dst = malloc((count-skip) * to_width * gl_sizeof(to)); GLvoid *dst = malloc((count-skip) * to_width * gl_sizeof(to));
GLsizei from_size = gl_sizeof(from) * width; GLsizei from_size = gl_sizeof(from) * width;
GLsizei to_size = gl_sizeof(to) * to_width; GLsizei to_size = gl_sizeof(to) * to_width;
@@ -106,10 +142,12 @@ GLvoid *copy_gl_array_convert(const GLvoid *src,
) )
} else { } else {
GL_TYPE_SWITCH_MAX(out, dst, to, GL_TYPE_SWITCH_MAX(out, dst, to,
for (int i = skip; i < count; i++) { GL_TYPE_SWITCH2(input, in, from,
GL_TYPE_SWITCH(input, in, from, const GLuint maxf = gl_max_value(from);
for (int i = skip; i < count; i++)
,
for (j = 0; j < width; j++) { for (j = 0; j < width; j++) {
out[j] = input[j]*maxv/gl_max_value(from); out[j] = input[j]*maxv/maxf;
} }
for (; j < to_width-1; j++) { for (; j < to_width-1; j++) {
out[j]=0; out[j]=0;
@@ -119,12 +157,11 @@ GLvoid *copy_gl_array_convert(const GLvoid *src,
} }
out += to_width; out += to_width;
in += stride; in += stride;
, ,
default: default:
printf(unknown_str, from); printf(unknown_str, from);
return NULL; return NULL;
) ),
},
default: default:
printf(unknown_str, to); printf(unknown_str, to);
return NULL; return NULL;

View File

@@ -0,0 +1,59 @@
#include "debug.h"
#define p(a) \
case a: return #a
const char* PrintEnum(GLenum what) {
static char fallback[64];
switch(what)
{
// target
p(GL_TEXTURE_1D);
p(GL_TEXTURE_2D);
p(GL_TEXTURE_3D);
p(GL_FRAMEBUFFER);
p(GL_RENDERBUFFER);
p(GL_PROXY_TEXTURE_1D);
p(GL_PROXY_TEXTURE_2D);
p(GL_PROXY_TEXTURE_3D);
p(GL_READ_FRAMEBUFFER);
p(GL_DRAW_FRAMEBUFFER);
// format
p(GL_RED);
p(GL_RGB);
p(GL_RGBA);
p(GL_RGBA8);
p(GL_RGB8);
p(GL_COMPRESSED_RGB_S3TC_DXT1_EXT);
p(GL_COMPRESSED_RGBA_S3TC_DXT1_EXT);
p(GL_COMPRESSED_RGBA_S3TC_DXT3_EXT);
p(GL_COMPRESSED_RGBA_S3TC_DXT5_EXT);
// type
p(GL_UNSIGNED_BYTE);
p(GL_UNSIGNED_BYTE_2_3_3_REV);
p(GL_UNSIGNED_BYTE_3_3_2);
p(GL_UNSIGNED_INT);
p(GL_UNSIGNED_SHORT);
p(GL_UNSIGNED_SHORT_5_5_5_1);
p(GL_UNSIGNED_SHORT_1_5_5_5_REV);
p(GL_UNSIGNED_SHORT_4_4_4_4);
p(GL_UNSIGNED_SHORT_4_4_4_4_REV);
p(GL_UNSIGNED_SHORT_5_6_5);
p(GL_UNSIGNED_SHORT_5_6_5_REV);
p(GL_FLOAT);
p(GL_DOUBLE);
// texture pack/unpack
p(GL_UNPACK_ALIGNMENT);
// framebuffer
p(GL_COLOR_ATTACHMENT0);
p(GL_COLOR_ATTACHMENT1);
p(GL_COLOR_ATTACHMENT2);
p(GL_COLOR_ATTACHMENT3);
p(GL_COLOR_ATTACHMENT4);
p(GL_DEPTH_ATTACHMENT);
p(GL_STENCIL_ATTACHMENT);
default:
sprintf(fallback, "0x%04X", what);
}
return fallback;
}

View File

@@ -0,0 +1,8 @@
#ifndef __DEBUG_H_
#define __DEBUG_H_
#include "gl.h"
const char* PrintEnum(GLenum what);
#endif

View File

@@ -1,4 +1,5 @@
#include "framebuffers.h" #include "framebuffers.h"
#include "debug.h"
#ifndef ANDROID #ifndef ANDROID
#include <execinfo.h> #include <execinfo.h>
@@ -19,13 +20,19 @@ int mainfbo_height = 480;
int mainfbo_nwidth = 1024; int mainfbo_nwidth = 1024;
int mainfbo_nheight = 512; int mainfbo_nheight = 512;
extern bool g_recyclefbo;
GLuint fbo_read = 0; // if not 0, that's the READ only Framebuffer attached GLuint fbo_read = 0; // if not 0, that's the READ only Framebuffer attached
GLuint fbo_draw = 0; // if not 0, that's the DRAW only Framebuffer attached GLuint fbo_draw = 0; // if not 0, that's the DRAW only Framebuffer attached
GLuint *old_fbos = NULL;
int nbr_fbos = 0;
int cap_fbos = 0;
int npot(int n); int npot(int n);
void readfboBegin() { void readfboBegin() {
//printf("readfboBegin, fbo status read=%u, draw=%u, main=%u, current=%u\n", fbo_read, fbo_draw, mainfbo_fbo, current_fb); //printf("readfboBegin, fbo status read=%u, draw=%u, main=%u, current=%u\n", fbo_read, fbo_draw, mainfbo_fbo, current_fb);
LOAD_GLES_OES(glBindFramebuffer); LOAD_GLES_OES(glBindFramebuffer);
if (!(fbo_read || fbo_draw)) if (!(fbo_read || fbo_draw))
return; return;
@@ -36,7 +43,7 @@ void readfboBegin() {
} }
void readfboEnd() { void readfboEnd() {
//printf("readfboEnd, fbo status read=%u, draw=%u, main=%u, current=%u\n", fbo_read, fbo_draw, mainfbo_fbo, current_fb); //printf("readfboEnd, fbo status read=%u, draw=%u, main=%u, current=%u\n", fbo_read, fbo_draw, mainfbo_fbo, current_fb);
LOAD_GLES_OES(glBindFramebuffer); LOAD_GLES_OES(glBindFramebuffer);
if (!(fbo_read || fbo_draw)) if (!(fbo_read || fbo_draw))
return; return;
@@ -48,23 +55,44 @@ void readfboEnd() {
void glGenFramebuffers(GLsizei n, GLuint *ids) { void glGenFramebuffers(GLsizei n, GLuint *ids) {
LOAD_GLES_OES(glGenFramebuffers); LOAD_GLES_OES(glGenFramebuffers);
//printf("glGenFramebuffers(%i, %p)\n", n, ids); //printf("glGenFramebuffers(%i, %p)\n", n, ids);
GLsizei m = 0;
while(g_recyclefbo && (nbr_fbos>0) && (n-m>0)) {
//printf("Recycled 1 FBO\n");
ids[m++] = old_fbos[--nbr_fbos];
}
noerrorShim();
if(n-m == 0)
return;
errorGL(); errorGL();
gles_glGenFramebuffers(n, ids); gles_glGenFramebuffers(n-m, ids+m);
} }
void glDeleteFramebuffers(GLsizei n, GLuint *framebuffers) { void glDeleteFramebuffers(GLsizei n, GLuint *framebuffers) {
//printf("glDeleteFramebuffers(%i, %p), framebuffers[0]=%u\n", n, framebuffers, framebuffers[0]); //printf("glDeleteFramebuffers(%i, %p), framebuffers[0]=%u\n", n, framebuffers, framebuffers[0]);
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES_OES(glDeleteFramebuffers); if (g_recyclefbo) {
//printf("Recycling %i FBOs\n", n);
errorGL(); noerrorShim();
gles_glDeleteFramebuffers(n, framebuffers); if(cap_fbos == 0) {
cap_fbos = 16;
old_fbos = (GLuint*)malloc(cap_fbos * sizeof(GLuint));
}
if (nbr_fbos+n == cap_fbos) {
cap_fbos += n;
old_fbos = (GLuint*)realloc(old_fbos, cap_fbos *sizeof(GLuint));
}
memcpy(old_fbos+nbr_fbos, framebuffers, n*sizeof(GLuint));
nbr_fbos += n;
} else {
LOAD_GLES_OES(glDeleteFramebuffers);
errorGL();
gles_glDeleteFramebuffers(n, framebuffers);
}
} }
GLboolean glIsFramebuffer(GLuint framebuffer) { GLboolean glIsFramebuffer(GLuint framebuffer) {
//printf("glIsFramebuffer(%u)\n", framebuffer); //printf("glIsFramebuffer(%u)\n", framebuffer);
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES_OES(glIsFramebuffer); LOAD_GLES_OES(glIsFramebuffer);
@@ -92,7 +120,7 @@ GLenum glCheckFramebufferStatus(GLenum target) {
} }
void glBindFramebuffer(GLenum target, GLuint framebuffer) { void glBindFramebuffer(GLenum target, GLuint framebuffer) {
//printf("glBindFramebuffer(0x%04X, %u), list=%s\n", target, framebuffer, state.list.active?"active":"none"); //printf("glBindFramebuffer(%s, %u), list=%s\n", PrintEnum(target), framebuffer, state.list.active?"active":"none");
//PUSH_IF_COMPILING(glBindFramebuffer); //PUSH_IF_COMPILING(glBindFramebuffer);
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES_OES(glBindFramebuffer); LOAD_GLES_OES(glBindFramebuffer);
@@ -118,13 +146,16 @@ void glBindFramebuffer(GLenum target, GLuint framebuffer) {
fbo_draw = framebuffer; fbo_draw = framebuffer;
} }
if(target==GL_FRAMEBUFFER && framebuffer!=0) {
gles_glBindFramebuffer(target, 0);
gles_glCheckFramebufferStatus(target);
}
current_fb = framebuffer; current_fb = framebuffer;
if (mainfbo_fbo && (framebuffer==0)) if (mainfbo_fbo && (framebuffer==0))
framebuffer = mainfbo_fbo; framebuffer = mainfbo_fbo;
//errorGL();
//noerrorShim();
gles_glBindFramebuffer(target, framebuffer); gles_glBindFramebuffer(target, framebuffer);
GLenum err=gles_glGetError(); GLenum err=gles_glGetError();
errorShim(err); errorShim(err);
@@ -132,14 +163,17 @@ void glBindFramebuffer(GLenum target, GLuint framebuffer) {
fb_status = gles_glCheckFramebufferStatus(target); fb_status = gles_glCheckFramebufferStatus(target);
} }
void glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level) { void glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget, GLuint texture, GLint level) {
static GLuint scrap_tex = 0;
static int scrap_width = 0;
static int scrap_height = 0;
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES_OES(glFramebufferTexture2D); LOAD_GLES_OES(glFramebufferTexture2D);
LOAD_GLES(glTexImage2D); LOAD_GLES(glTexImage2D);
LOAD_GLES(glBindTexture); LOAD_GLES(glBindTexture);
//printf("glFramebufferTexture2D(0x%04X, 0x%04X, 0x%04X, %u, %i)\n", target, attachment, textarget, texture, level); //printf("glFramebufferTexture2D(%s, %s, %s, %u, %i)\n", PrintEnum(target), PrintEnum(attachment), PrintEnum(textarget), texture, level);
if (level!=0)
return;
// Ignore Color attachment 1 .. 9 // Ignore Color attachment 1 .. 9
if ((attachment>=GL_COLOR_ATTACHMENT0+1) && (attachment<=GL_COLOR_ATTACHMENT0+9)) { if ((attachment>=GL_COLOR_ATTACHMENT0+1) && (attachment<=GL_COLOR_ATTACHMENT0+9)) {
@@ -147,6 +181,7 @@ void glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget,
return; return;
} }
int twidth = 0, theight = 0;
// find texture and get it's real name // find texture and get it's real name
if (texture) { if (texture) {
gltexture_t *tex = NULL; gltexture_t *tex = NULL;
@@ -162,7 +197,7 @@ void glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget,
k = kh_get(tex, list, texture); k = kh_get(tex, list, texture);
if (k == kh_end(list)){ if (k == kh_end(list)){
//printf("*WARNING* texture for FBO not found, name=%u\n", texture); printf("*WARNING* texture for FBO not found, name=%u\n", texture);
} else { } else {
tex = kh_value(list, k); tex = kh_value(list, k);
texture = tex->glname; texture = tex->glname;
@@ -180,6 +215,8 @@ void glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget,
gles_glTexImage2D(GL_TEXTURE_2D, 0, tex->format, tex->nwidth, tex->nheight, 0, tex->format, tex->type, NULL); gles_glTexImage2D(GL_TEXTURE_2D, 0, tex->format, tex->nwidth, tex->nheight, 0, tex->format, tex->type, NULL);
if (oldtex!=tex->glname) gles_glBindTexture(GL_TEXTURE_2D, oldtex); if (oldtex!=tex->glname) gles_glBindTexture(GL_TEXTURE_2D, oldtex);
} }
twidth = tex->nwidth;
theight = tex->nheight;
/* if ((tex->width<32) || (tex->height<32)) { /* if ((tex->width<32) || (tex->height<32)) {
printf("LIBGL: enlarging too-small texture for FBO\n"); printf("LIBGL: enlarging too-small texture for FBO\n");
tex->nwidth = (tex->nwidth<32)?32:tex->nwidth; tex->nwidth = (tex->nwidth<32)?32:tex->nwidth;
@@ -191,10 +228,29 @@ void glFramebufferTexture2D(GLenum target, GLenum attachment, GLenum textarget,
gles_glTexImage2D(GL_TEXTURE_2D, 0, tex->format, tex->nwidth, tex->nheight, 0, tex->format, tex->type, NULL); gles_glTexImage2D(GL_TEXTURE_2D, 0, tex->format, tex->nwidth, tex->nheight, 0, tex->format, tex->type, NULL);
if (oldtex!=tex->glname) gles_glBindTexture(GL_TEXTURE_2D, oldtex); if (oldtex!=tex->glname) gles_glBindTexture(GL_TEXTURE_2D, oldtex);
}*/ }*/
//printf("found texture, glname=%u, size=%ix%i(%ix%i), format/type=0x%04X/0x%04X\n", texture, tex->width, tex->height, tex->nwidth, tex->nheight, tex->format, tex->type); //printf("found texture, glname=%u, size=%ix%i(%ix%i), format/type=0x%04X/0x%04X\n", texture, tex->width, tex->height, tex->nwidth, tex->nheight, tex->format, tex->type);
} }
} }
twidth = twidth >> level; if(twidth<1) twidth=1;
theight = theight >> level; if(theight<1) theight=1;
if (level!=0) {
//bind a scrap texture, we don't want level != 0 binding on GLES
if(!scrap_tex)
glGenTextures(1, &scrap_tex);
if ((scrap_width!=twidth) || (scrap_height!=theight)) {
scrap_width = twidth;
scrap_height = theight;
gltexture_t *bound = state.texture.bound[state.texture.active];
GLuint oldtex = (bound)?bound->glname:0;
if (oldtex!=scrap_tex) gles_glBindTexture(GL_TEXTURE_2D, scrap_tex);
gles_glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, scrap_width, scrap_height, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
if (oldtex!=scrap_tex) gles_glBindTexture(GL_TEXTURE_2D, oldtex);
}
texture = scrap_tex;
}
errorGL(); errorGL();
gles_glFramebufferTexture2D(target, attachment, textarget, texture, 0); gles_glFramebufferTexture2D(target, attachment, textarget, texture, 0);
} }
@@ -209,7 +265,7 @@ void glFramebufferTexture3D(GLenum target, GLenum attachment, GLenum textarget,
void glGenRenderbuffers(GLsizei n, GLuint *renderbuffers) { void glGenRenderbuffers(GLsizei n, GLuint *renderbuffers) {
LOAD_GLES_OES(glGenRenderbuffers); LOAD_GLES_OES(glGenRenderbuffers);
//printf("glGenRenderbuffers(%i, %p)\n", n, renderbuffers); //printf("glGenRenderbuffers(%i, %p)\n", n, renderbuffers);
errorGL(); errorGL();
gles_glGenRenderbuffers(n, renderbuffers); gles_glGenRenderbuffers(n, renderbuffers);
@@ -218,9 +274,9 @@ void glGenRenderbuffers(GLsizei n, GLuint *renderbuffers) {
void glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer) { void glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum renderbuffertarget, GLuint renderbuffer) {
LOAD_GLES_OES(glFramebufferRenderbuffer); LOAD_GLES_OES(glFramebufferRenderbuffer);
LOAD_GLES_OES(glGetFramebufferAttachmentParameteriv); LOAD_GLES_OES(glGetFramebufferAttachmentParameteriv);
//printf("glFramebufferRenderbuffer(0x%04X, 0x%04X, 0x%04X, %u)\n", target, attachment, renderbuffertarget, renderbuffer); //printf("glFramebufferRenderbuffer(%s, %s, %s, %u)\n", PrintEnum(target), PrintEnum(attachment), PrintEnum(renderbuffertarget), renderbuffer);
//TODO: handle target=READBUFFER or DRAWBUFFER... //TODO: handle target=READBUFFER or DRAWBUFFER...
if (depthstencil && (attachment==GL_STENCIL_ATTACHMENT)) { if (depthstencil && (attachment==GL_STENCIL_ATTACHMENT)) {
khint_t k = kh_get(dsr, depthstencil, renderbuffer); khint_t k = kh_get(dsr, depthstencil, renderbuffer);
if (k != kh_end(depthstencil)) { if (k != kh_end(depthstencil)) {
@@ -235,15 +291,7 @@ void glFramebufferRenderbuffer(GLenum target, GLenum attachment, GLenum renderbu
noerrorShim(); noerrorShim();
return; return;
} }
if ((current_fb!=0) && (renderbuffer!=0) && ((attachment==GL_DEPTH_ATTACHMENT) || (attachment==GL_STENCIL_ATTACHMENT))) {
GLuint tmp;
gles_glGetFramebufferAttachmentParameteriv(target, attachment, GL_FRAMEBUFFER_ATTACHMENT_OBJECT_NAME, &tmp);
if (tmp==renderbuffer) {
noerrorShim();
return;
}
}
errorGL(); errorGL();
gles_glFramebufferRenderbuffer(target, attachment, renderbuffertarget, renderbuffer); gles_glFramebufferRenderbuffer(target, attachment, renderbuffertarget, renderbuffer);
} }
@@ -278,7 +326,7 @@ void glRenderbufferStorage(GLenum target, GLenum internalformat, GLsizei width,
LOAD_GLES_OES(glRenderbufferStorage); LOAD_GLES_OES(glRenderbufferStorage);
LOAD_GLES_OES(glGenRenderbuffers); LOAD_GLES_OES(glGenRenderbuffers);
LOAD_GLES_OES(glBindRenderbuffer); LOAD_GLES_OES(glBindRenderbuffer);
//printf("glRenderbufferStorage(0x%04X, 0x%04X, %i, %i)\n", target, internalformat, width, height); //printf("glRenderbufferStorage(0x%04X, 0x%04X, %i, %i)\n", target, internalformat, width, height);
errorGL(); errorGL();
width = npot(width); width = npot(width);
@@ -325,7 +373,7 @@ void glRenderbufferStorageMultisample(GLenum target, GLsizei samples, GLenum int
void glBindRenderbuffer(GLenum target, GLuint renderbuffer) { void glBindRenderbuffer(GLenum target, GLuint renderbuffer) {
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES_OES(glBindRenderbuffer); LOAD_GLES_OES(glBindRenderbuffer);
//printf("glBindRenderbuffer(0x%04X, %u)\n", target, renderbuffer); //printf("glBindRenderbuffer(%s, %u), binded Fbo=%u\n", PrintEnum(target), renderbuffer, current_fb);
current_rb = renderbuffer; current_rb = renderbuffer;
@@ -334,7 +382,7 @@ void glBindRenderbuffer(GLenum target, GLuint renderbuffer) {
} }
GLboolean glIsRenderbuffer(GLuint renderbuffer) { GLboolean glIsRenderbuffer(GLuint renderbuffer) {
//printf("glIsRenderbuffer(%u)\n", renderbuffer); //printf("glIsRenderbuffer(%u)\n", renderbuffer);
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES_OES(glIsRenderbuffer); LOAD_GLES_OES(glIsRenderbuffer);
@@ -343,7 +391,7 @@ GLboolean glIsRenderbuffer(GLuint renderbuffer) {
} }
void glGenerateMipmap(GLenum target) { void glGenerateMipmap(GLenum target) {
//printf("glGenerateMipmap(0x%04X)\n", target); //printf("glGenerateMipmap(0x%04X)\n", target);
LOAD_GLES_OES(glGenerateMipmap); LOAD_GLES_OES(glGenerateMipmap);
errorGL(); errorGL();
@@ -351,6 +399,7 @@ void glGenerateMipmap(GLenum target) {
} }
void glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attachment, GLenum pname, GLint *params) { void glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attachment, GLenum pname, GLint *params) {
//printf("glGetFramebufferAttachmentParameteriv(%s, %s, %s, %p)\n", PrintEnum(target), PrintEnum(attachment), PrintEnum(pname), params);
LOAD_GLES_OES(glGetFramebufferAttachmentParameteriv); LOAD_GLES_OES(glGetFramebufferAttachmentParameteriv);
errorGL(); errorGL();
@@ -358,6 +407,7 @@ void glGetFramebufferAttachmentParameteriv(GLenum target, GLenum attachment, GLe
} }
void glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint * params) { void glGetRenderbufferParameteriv(GLenum target, GLenum pname, GLint * params) {
//printf("glGetRenderbufferParameteriv(%s, %s, %p)\n", PrintEnum(target), PrintEnum(pname), params);
LOAD_GLES_OES(glGetRenderbufferParameteriv); LOAD_GLES_OES(glGetRenderbufferParameteriv);
errorGL(); errorGL();
@@ -381,10 +431,12 @@ void createMainFBO(int width, int height) {
LOAD_GLES(glClientActiveTexture); LOAD_GLES(glClientActiveTexture);
LOAD_GLES(glClear); LOAD_GLES(glClear);
// If there is already a Framebuffer created, let's delete it.... // If there is already a Framebuffer created, let's delete it.... unless it's already the right size!
if (mainfbo_fbo) if (mainfbo_fbo) {
if (width==mainfbo_width && height==mainfbo_height)
return;
deleteMainFBO(); deleteMainFBO();
}
// switch to texture unit 0 if needed // switch to texture unit 0 if needed
if (state.texture.active != 0) if (state.texture.active != 0)
gles_glActiveTexture(GL_TEXTURE0); gles_glActiveTexture(GL_TEXTURE0);
@@ -463,10 +515,12 @@ void blitMainFBO() {
return; return;
// switch to texture unit 0 if needed // switch to texture unit 0 if needed
int old_tex = state.texture.active;
int old_client = state.texture.client;
if (state.texture.active != 0) if (state.texture.active != 0)
gles_glActiveTexture(GL_TEXTURE0); glActiveTexture(GL_TEXTURE0);
if (state.texture.client != 0) if (state.texture.client != 0)
gles_glClientActiveTexture(GL_TEXTURE0); glClientActiveTexture(GL_TEXTURE0);
// bind the FBO texture // bind the FBO texture
gles_glEnable(GL_TEXTURE_2D); gles_glEnable(GL_TEXTURE_2D);
gles_glBindTexture(GL_TEXTURE_2D, mainfbo_tex); gles_glBindTexture(GL_TEXTURE_2D, mainfbo_tex);
@@ -475,7 +529,7 @@ void blitMainFBO() {
gles_glGetIntegerv(GL_VIEWPORT, old_vp); gles_glGetIntegerv(GL_VIEWPORT, old_vp);
gles_glViewport(0, 0, mainfbo_width, mainfbo_height); gles_glViewport(0, 0, mainfbo_width, mainfbo_height);
// Draw the texture // Draw the texture
#if 1 #if 0
gles_glDrawTexi(0, 0, 0, mainfbo_width, mainfbo_height); gles_glDrawTexi(0, 0, 0, mainfbo_width, mainfbo_height);
#else #else
{ {
@@ -485,33 +539,29 @@ void blitMainFBO() {
LOAD_GLES(glVertexPointer); LOAD_GLES(glVertexPointer);
LOAD_GLES(glTexCoordPointer); LOAD_GLES(glTexCoordPointer);
LOAD_GLES(glDrawArrays); LOAD_GLES(glDrawArrays);
LOAD_GLES(glOrthof);
LOAD_GLES(glPushMatrix);
LOAD_GLES(glPopMatrix);
glPushAttrib(GL_TEXTURE_BIT | GL_ENABLE_BIT | GL_TRANSFORM_BIT | GL_COLOR_BUFFER_BIT | GL_CURRENT_BIT); glPushAttrib(GL_TEXTURE_BIT | GL_ENABLE_BIT | GL_TRANSFORM_BIT | GL_COLOR_BUFFER_BIT | GL_CURRENT_BIT);
GLfloat old_projection[16], old_modelview[16], old_texture[16];
glMatrixMode(GL_TEXTURE); glMatrixMode(GL_TEXTURE);
glGetFloatv(GL_TEXTURE_MATRIX, old_texture); gles_glPushMatrix();
glLoadIdentity(); glLoadIdentity();
glMatrixMode(GL_PROJECTION); glMatrixMode(GL_PROJECTION);
glGetFloatv(GL_PROJECTION_MATRIX, old_projection); gles_glPushMatrix();
glLoadIdentity(); glLoadIdentity();
glMatrixMode(GL_MODELVIEW); glMatrixMode(GL_MODELVIEW);
glGetFloatv(GL_MODELVIEW_MATRIX, old_modelview); gles_glPushMatrix();
glLoadIdentity(); glLoadIdentity();
float w2 = 800 / 2.0f;
float h2 = 480 / 2.0f;
float x1=0;
float x2=mainfbo_width;
float y1=0;
float y2=mainfbo_height;
GLfloat vert[] = { GLfloat vert[] = {
(x1-w2)/w2, (y1-h2)/h2, 0, -1, -1,
(x2-w2)/w2, (y1-h2)/h2, 0, +1, -1,
(x2-w2)/w2, (y2-h2)/h2, 0, +1, +1,
(x1-w2)/w2, (y2-h2)/h2, 0, -1, +1,
}; };
float sw = mainfbo_width / mainfbo_nwidth; float sw = (float)mainfbo_width / (float)mainfbo_nwidth;
float sh = mainfbo_height / mainfbo_nheight; float sh = (float)mainfbo_height / (float)mainfbo_nheight;
GLfloat tex[] = { GLfloat tex[] = {
0, 0, 0, 0,
sw, 0, sw, 0,
@@ -519,35 +569,35 @@ void blitMainFBO() {
0, sh 0, sh
}; };
glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT | GL_CLIENT_PIXEL_STORE_BIT); glPushClientAttrib(GL_CLIENT_VERTEX_ARRAY_BIT);
glDisable(GL_DEPTH_TEST); glDisable(GL_DEPTH_TEST);
glDisable(GL_LIGHTING); glDisable(GL_LIGHTING);
glDisable(GL_CULL_FACE); glDisable(GL_CULL_FACE);
glEnable(GL_ALPHA_TEST); glDisable(GL_ALPHA_TEST);
glAlphaFunc(GL_GREATER, 0.0f); glDisable(GL_BLEND);
glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE); // glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
gles_glEnableClientState(GL_VERTEX_ARRAY); glEnableClientState(GL_VERTEX_ARRAY);
gles_glEnableClientState(GL_TEXTURE_COORD_ARRAY); glEnableClientState(GL_TEXTURE_COORD_ARRAY);
gles_glDisableClientState(GL_COLOR_ARRAY); glDisableClientState(GL_COLOR_ARRAY);
gles_glDisableClientState(GL_NORMAL_ARRAY); glDisableClientState(GL_NORMAL_ARRAY);
gles_glVertexPointer(3, GL_FLOAT, 0, vert); gles_glVertexPointer(2, GL_FLOAT, 0, vert);
gles_glTexCoordPointer(2, GL_FLOAT, 0, tex); gles_glTexCoordPointer(2, GL_FLOAT, 0, tex);
//glColor4f(1.0f, 1.0f, 1.0f, 1.0f); glColor4f(1.0f, 1.0f, 1.0f, 1.0f);
gles_glDrawArrays(GL_TRIANGLE_FAN, 0, 4); gles_glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
// All the previous states are Pushed / Poped anyway... // All the previous states are Pushed / Poped anyway...
glPopClientAttrib(); glPopClientAttrib();
glMatrixMode(GL_TEXTURE);
glLoadMatrixf(old_texture);
glMatrixMode(GL_MODELVIEW); glMatrixMode(GL_MODELVIEW);
glLoadMatrixf(old_modelview); gles_glPopMatrix();
glMatrixMode(GL_PROJECTION); glMatrixMode(GL_PROJECTION);
glLoadMatrixf(old_projection); gles_glPopMatrix();
glMatrixMode(GL_TEXTURE);
gles_glPopMatrix();
glPopAttrib(); glPopAttrib();
} }
#endif #endif
@@ -560,10 +610,10 @@ void blitMainFBO() {
gles_glBindTexture(GL_TEXTURE_2D, 0); gles_glBindTexture(GL_TEXTURE_2D, 0);
if (!state.enable.texture_2d[0]) if (!state.enable.texture_2d[0])
gles_glDisable(GL_TEXTURE_2D); gles_glDisable(GL_TEXTURE_2D);
if (state.texture.active != 0) if (old_tex != 0)
gles_glActiveTexture(GL_TEXTURE0 + state.texture.active); glActiveTexture(GL_TEXTURE0 + old_tex);
if (state.texture.client != 0) if (old_client != 0)
gles_glClientActiveTexture(GL_TEXTURE0 + state.texture.client); glClientActiveTexture(GL_TEXTURE0 + old_client);
} }
void bindMainFBO() { void bindMainFBO() {

View File

@@ -71,21 +71,16 @@ void initialize_glshim() {
// config functions // config functions
const GLubyte *glGetString(GLenum name) { const GLubyte *glGetString(GLenum name) {
LOAD_GLES(glGetString); // LOAD_GLES(glGetString);
const GLubyte *str; const GLubyte *str;
errorShim(GL_NO_ERROR); errorShim(GL_NO_ERROR);
if ((str=gles_glGetString(name))==NULL) /* if ((str=gles_glGetString(name))==NULL)
printf("**warning** glGetString(%i) called with bad init\n", name); printf("**warning** glGetString(%i) called with bad init\n", name);*/
switch (name) { switch (name) {
case GL_VERSION: case GL_VERSION:
#ifdef USE_ES2
return (GLubyte *)"4.3 glshim wrapper";
#else
return (GLubyte *)"1.5 glshim wrapper"; return (GLubyte *)"1.5 glshim wrapper";
#endif
case GL_EXTENSIONS: case GL_EXTENSIONS:
return (const GLubyte *)(char *){ return (const GLubyte *)(char *){
#ifndef USE_ES2
"GL_ARB_vertex_buffer_object " "GL_ARB_vertex_buffer_object "
"GL_ARB_vertex_buffer " "GL_ARB_vertex_buffer "
"GL_EXT_vertex_array " "GL_EXT_vertex_array "
@@ -124,24 +119,13 @@ const GLubyte *glGetString(GLenum name) {
// "GL_EXT_blend_logic_op " // "GL_EXT_blend_logic_op "
// "GL_EXT_blend_color " // "GL_EXT_blend_color "
// "GL_ARB_texture_cube_map " // "GL_ARB_texture_cube_map "
#else
"GL_ARB_vertex_shader "
"GL_ARB_fragment_shader "
"GL_ARB_vertex_buffer_object "
"GL_EXT_framebuffer_object "
"GL_EXT_vertex_array "
#endif
}; };
case GL_VENDOR: case GL_VENDOR:
return (GLubyte *)"OpenPandora"; return (GLubyte *)"OpenPandora";
case GL_RENDERER: case GL_RENDERER:
#ifdef USE_ES2
return (GLubyte *)"GLESv2 wrapper";
#else
return (GLubyte *)"GLES_CM wrapper"; return (GLubyte *)"GLES_CM wrapper";
case GL_SHADING_LANGUAGE_VERSION: case GL_SHADING_LANGUAGE_VERSION:
return (GLubyte *)""; return (GLubyte *)"";
#endif
default: default:
errorShim(GL_INVALID_ENUM); errorShim(GL_INVALID_ENUM);
return (str)?str:(GLubyte*)""; return (str)?str:(GLubyte*)"";
@@ -436,6 +420,7 @@ static void proxy_glEnable(GLenum cap, bool enable, void (*next)(GLenum)) {
state.enable.texture_2d[state.texture.active] = enable; state.enable.texture_2d[state.texture.active] = enable;
#endif #endif
switch (cap) { switch (cap) {
enable(GL_AUTO_NORMAL, auto_normal);
proxy_enable(GL_BLEND, blend); proxy_enable(GL_BLEND, blend);
proxy_enable(GL_TEXTURE_2D, texture_2d[state.texture.active]); proxy_enable(GL_TEXTURE_2D, texture_2d[state.texture.active]);
enable(GL_TEXTURE_GEN_S, texgen_s[state.texture.active]); enable(GL_TEXTURE_GEN_S, texgen_s[state.texture.active]);
@@ -541,35 +526,34 @@ void glDisableClientState(GLenum cap) {
} }
#endif #endif
#define isenabled(what, where) \
case what: return state.enable.where
GLboolean glIsEnabled(GLenum cap) { GLboolean glIsEnabled(GLenum cap) {
// should flush for now... to be optimized later! // should flush for now... to be optimized later!
if (state.gl_batch) flush(); if (state.gl_batch) flush();
LOAD_GLES(glIsEnabled); LOAD_GLES(glIsEnabled);
noerrorShim(); noerrorShim();
switch (cap) { switch (cap) {
case GL_LINE_STIPPLE: isenabled(GL_AUTO_NORMAL, auto_normal);
return state.enable.line_stipple; isenabled(GL_LINE_STIPPLE, line_stipple);
case GL_TEXTURE_GEN_S: isenabled(GL_TEXTURE_GEN_S, texgen_s[state.texture.active]);
return state.enable.texgen_s[state.texture.active]; isenabled(GL_TEXTURE_GEN_T, texgen_t[state.texture.active]);
case GL_TEXTURE_GEN_T: isenabled(GL_TEXTURE_GEN_R, texgen_r[state.texture.active]);
return state.enable.texgen_t[state.texture.active]; isenabled(GL_COLOR_SUM, color_sum);
case GL_TEXTURE_GEN_R: isenabled(GL_SECONDARY_COLOR_ARRAY, secondary_array);
return state.enable.texgen_t[state.texture.active]; isenabled(GL_TEXTURE_1D, texture_1d[state.texture.active]);
case GL_TEXTURE_COORD_ARRAY: isenabled(GL_TEXTURE_3D, texture_3d[state.texture.active]);
return state.enable.tex_coord_array[state.texture.client]; isenabled(GL_VERTEX_ARRAY, vertex_array);
case GL_COLOR_SUM: isenabled(GL_NORMAL_ARRAY, normal_array);
return state.enable.color_sum; isenabled(GL_COLOR_ARRAY, color_array);
case GL_SECONDARY_COLOR_ARRAY: isenabled(GL_TEXTURE_COORD_ARRAY, tex_coord_array[state.texture.client]);
return state.enable.secondary_array;
case GL_TEXTURE_1D:
return state.enable.texture_1d[state.texture.active];
case GL_TEXTURE_3D:
return state.enable.texture_1d[state.texture.active];
default: default:
errorGL(); errorGL();
return gles_glIsEnabled(cap); return gles_glIsEnabled(cap);
} }
} }
#undef isenabled
static renderlist_t *arrays_to_renderlist(renderlist_t *list, GLenum mode, static renderlist_t *arrays_to_renderlist(renderlist_t *list, GLenum mode,
GLsizei skip, GLsizei count) { GLsizei skip, GLsizei count) {
@@ -648,7 +632,7 @@ void glDrawElements(GLenum mode, GLsizei count, GLenum type, const GLvoid *indic
list->indices = sindices; list->indices = sindices;
list->ilen = count; list->ilen = count;
list->indice_cap = count; list->indice_cap = count;
end_renderlist(list); //end_renderlist(list);
state.list.active = extend_renderlist(list); state.list.active = extend_renderlist(list);
return; return;
@@ -1371,12 +1355,12 @@ void glEndList() {
state.list.compiling = false; state.list.compiling = false;
end_renderlist(state.list.active); end_renderlist(state.list.active);
state.list.active = NULL; state.list.active = NULL;
if (gl_batch==1) {
init_batch();
}
if (state.list.mode == GL_COMPILE_AND_EXECUTE) { if (state.list.mode == GL_COMPILE_AND_EXECUTE) {
glCallList(list); glCallList(list);
} }
if (gl_batch) {
init_batch();
}
} }
} }
@@ -1437,6 +1421,9 @@ void glCallLists(GLsizei n, GLenum type, const GLvoid *lists) {
} }
void glDeleteList(GLuint list) { void glDeleteList(GLuint list) {
if(state.gl_batch) {
flush();
}
renderlist_t *l = glGetList(list); renderlist_t *l = glGetList(list);
if (l) { if (l) {
free_renderlist(l); free_renderlist(l);

View File

@@ -201,6 +201,15 @@ static void load_egl_lib() {
break; \ break; \
} }
#define GL_TYPE_CASE2(name, var, magic, type, code2, code) \
case magic: { \
code2 { \
type *name = (type *)var; \
code \
} \
break; \
}
#define GL_TYPE_CASE_MAX(name, var, magic, type, code, max) \ #define GL_TYPE_CASE_MAX(name, var, magic, type, code, max) \
case magic: { \ case magic: { \
type *name = (type *)var; \ type *name = (type *)var; \
@@ -222,6 +231,19 @@ static void load_egl_lib() {
extra \ extra \
} }
#define GL_TYPE_SWITCH2(name, var, type, code2, code, extra) \
switch (type) { \
GL_TYPE_CASE2(name, var, GL_DOUBLE, GLdouble, code2, code) \
GL_TYPE_CASE2(name, var, GL_FLOAT, GLfloat, code2, code) \
GL_TYPE_CASE2(name, var, GL_INT, GLint, code2, code) \
GL_TYPE_CASE2(name, var, GL_SHORT, GLshort, code2, code) \
GL_TYPE_CASE2(name, var, GL_BYTE, GLbyte, code2, code) \
GL_TYPE_CASE2(name, var, GL_UNSIGNED_BYTE, GLubyte, code2, code) \
GL_TYPE_CASE2(name, var, GL_UNSIGNED_INT, GLuint, code2, code) \
GL_TYPE_CASE2(name, var, GL_UNSIGNED_SHORT, GLushort, code2, code) \
extra \
}
#define GL_TYPE_SWITCH_MAX(name, var, type, code, extra) \ #define GL_TYPE_SWITCH_MAX(name, var, type, code, extra) \
switch (type) { \ switch (type) { \
GL_TYPE_CASE_MAX(name, var, GL_DOUBLE, GLdouble, code, 1.0d) \ GL_TYPE_CASE_MAX(name, var, GL_DOUBLE, GLdouble, code, 1.0d) \

View File

@@ -726,13 +726,7 @@ void draw_renderlist(renderlist_t *list) {
khash_t(texgen) *tgn = list->texgen; khash_t(texgen) *tgn = list->texgen;
rendertexgen_t *m; rendertexgen_t *m;
kh_foreach_value(tgn, m, kh_foreach_value(tgn, m,
switch (m->pname) { glTexGenfv(m->coord, m->pname, m->color);
case GL_TEXTURE_GEN_MODE:
glTexGeni(m->coord, m->pname, m->color[0]);
break;
default:
glTexGenfv(m->coord, m->pname, m->color);
}
) )
} }
@@ -853,74 +847,76 @@ void draw_renderlist(renderlist_t *list) {
if (state.polygon_mode == GL_LINE && list->mode_init>=GL_TRIANGLES) { if (state.polygon_mode == GL_LINE && list->mode_init>=GL_TRIANGLES) {
int n, s; int n, s;
int ilen = list->ilen; int ilen = list->ilen;
GLushort ind_line[ilen*3+1]; GLushort ind_line[ilen*4+2];
int k=0; int k=0;
switch (list->mode_init) { switch (list->mode_init) {
case GL_TRIANGLES: case GL_TRIANGLES:
// 1 triangle -> 3 lines if(ilen>2) {
for (int i = 0; i<ilen; i+=3) { // 1 triangle -> 3 lines
ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1]; for (int i = 0; i<ilen-2; i+=3) {
ind_line[k++] = indices[i+1]; ind_line[k++] = indices[i+2]; ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1];
ind_line[k++] = indices[i+2]; ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1]; ind_line[k++] = indices[i+2];
ind_line[k++] = indices[i+2]; ind_line[k++] = indices[i+0];
}
} }
break; break;
case GL_TRIANGLE_STRIP: case GL_TRIANGLE_STRIP:
// first 3 points a triangle, then a 2 lines per new point // first 3 points a triangle, then a 2 lines per new point
if (ilen>2) { if (ilen>2) {
ind_line[k++] = indices[0]; ind_line[k++] = indices[1]; ind_line[k++] = indices[0]; ind_line[k++] = indices[1];
} for (int i = 2; i<ilen; i++) {
for (int i = 2; i<ilen; i++) { ind_line[k++] = indices[i-2]; ind_line[k++] = indices[i];
ind_line[k++] = indices[i-2]; ind_line[k++] = indices[i]; ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i];
ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i]; }
} }
break; break;
case GL_TRIANGLE_FAN: case GL_TRIANGLE_FAN:
// first 3 points a triangle, then a 2 lines per new point too // first 3 points a triangle, then a 2 lines per new point too
if (ilen>2) { if (ilen>2) {
ind_line[k++] = indices[0]; ind_line[k++] = indices[1]; ind_line[k++] = indices[0]; ind_line[k++] = indices[1];
} for (int i = 2; i<ilen; i++) {
for (int i = 2; i<ilen; i++) { ind_line[k++] = indices[0]; ind_line[k++] = indices[i];
ind_line[k++] = indices[0]; ind_line[k++] = indices[i]; ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i];
ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i]; }
} }
break; break;
case GL_QUADS: case GL_QUADS:
// 4 lines per quads, but dest may already be a triangles list... if (ilen>3) {
if (list->mode == GL_TRIANGLE_FAN) { // 4 lines per quads, but dest may already be a triangles list...
// just 1 Quad if (list->mode == GL_TRIANGLE_FAN) {
for (int i=0; i<4; i++) { // just 1 Quad
ind_line[k++] = indices[i+0]; ind_line[k++] = indices[(i+1)%4]; for (int i=0; i<4; i++) {
} ind_line[k++] = indices[i+0]; ind_line[k++] = indices[(i+1)%4];
} else { }
// list of triangles, 2 per quads... } else {
for (int i=0; i<ilen; i+=6) { // list of triangles, 2 per quads...
ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1]; for (int i=0; i<ilen-5; i+=6) {
ind_line[k++] = indices[i+1]; ind_line[k++] = indices[i+2]; ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1];
ind_line[k++] = indices[i+2]; ind_line[k++] = indices[i+5]; ind_line[k++] = indices[i+1]; ind_line[k++] = indices[i+2];
ind_line[k++] = indices[i+5]; ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+2]; ind_line[k++] = indices[i+5];
ind_line[k++] = indices[i+5]; ind_line[k++] = indices[i+0];
}
} }
} }
break; break;
case GL_QUAD_STRIP: case GL_QUAD_STRIP:
// first 4 points is a quad, then 2 points per new quad // first 4 points is a quad, then 2 points per new quad
if (ilen>2) { if (ilen>3) {
ind_line[k++] = indices[0]; ind_line[k++] = indices[1]; ind_line[k++] = indices[0]; ind_line[k++] = indices[1];
} for (int i = 2; i<ilen-1; i+=2) {
for (int i = 2; i<ilen; i+=2) { ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i];
ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i]; ind_line[k++] = indices[i-2]; ind_line[k++] = indices[i+1];
ind_line[k++] = indices[i-2]; ind_line[k++] = indices[i+1]; ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1];
ind_line[k++] = indices[i+0]; ind_line[k++] = indices[i+1]; }
} }
break; break;
case GL_POLYGON: case GL_POLYGON:
// if polygons have been merged, then info is lost... // if polygons have been merged, then info is lost...
if (ilen) { if (ilen) {
ind_line[k++] = indices[0]; ind_line[k++] = indices[1]; ind_line[k++] = indices[0]; ind_line[k++] = indices[1];
} for (int i = 1; i<ilen; i++) {
for (int i = 1; i<ilen; i++) { ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i];
ind_line[k++] = indices[i-1]; ind_line[k++] = indices[i]; }
}
if (ilen) {
ind_line[k++] = indices[ilen-1]; ind_line[k++] = indices[0]; ind_line[k++] = indices[ilen-1]; ind_line[k++] = indices[0];
} }
break; break;
@@ -943,68 +939,78 @@ void draw_renderlist(renderlist_t *list) {
int len = list->len; int len = list->len;
if ((state.polygon_mode == GL_LINE) && (list->mode_init>=GL_TRIANGLES)) { if ((state.polygon_mode == GL_LINE) && (list->mode_init>=GL_TRIANGLES)) {
int n, s; int n, s;
GLushort ind_line[len*3+1]; GLushort ind_line[len*4+2];
int k=0; int k=0;
switch (list->mode_init) { switch (list->mode_init) {
case GL_TRIANGLES: case GL_TRIANGLES:
// 1 triangle -> 3 lines // 1 triangle -> 3 lines
for (int i = 0; i<len; i+=3) { if(len>2) {
ind_line[k++] = i+0; ind_line[k++] = i+1; for (int i = 0; i<len-2; i+=3) {
ind_line[k++] = i+1; ind_line[k++] = i+2; ind_line[k++] = i+0; ind_line[k++] = i+1;
ind_line[k++] = i+2; ind_line[k++] = i+0; ind_line[k++] = i+1; ind_line[k++] = i+2;
ind_line[k++] = i+2; ind_line[k++] = i+0;
}
} }
break; break;
case GL_TRIANGLE_STRIP: case GL_TRIANGLE_STRIP:
// first 3 points a triangle, then a 2 lines per new point // first 3 points a triangle, then a 2 lines per new point
if (len>2) { if (len>2) {
ind_line[k++] = 0; ind_line[k++] = 1; ind_line[k++] = 0; ind_line[k++] = 1;
} for (int i = 2; i<len; i++) {
for (int i = 2; i<len; i++) { ind_line[k++] = i-2; ind_line[k++] = i;
ind_line[k++] = i-2; ind_line[k++] = i; ind_line[k++] = i-1; ind_line[k++] = i;
ind_line[k++] = i-1; ind_line[k++] = i; }
} }
break; break;
case GL_TRIANGLE_FAN: case GL_TRIANGLE_FAN:
// first 3 points a triangle, then a 2 lines per new point too // first 3 points a triangle, then a 2 lines per new point too
if (len>2) { if (len>2) {
ind_line[k++] = 0; ind_line[k++] = 1; ind_line[k++] = 0; ind_line[k++] = 1;
} for (int i = 2; i<len; i++) {
for (int i = 2; i<len; i++) { ind_line[k++] = 0; ind_line[k++] = i;
ind_line[k++] = 0; ind_line[k++] = i; ind_line[k++] = i-1; ind_line[k++] = i;
ind_line[k++] = i-1; ind_line[k++] = i; }
} }
break; break;
case GL_QUADS: case GL_QUADS:
// 4 lines per quads, QUAD without indices means 1 single quad if(len>3) {
if (list->mode == GL_TRIANGLE_FAN) { // 4 lines per quads, QUAD without indices means 1 single quad
// just 1 Quad if (list->mode == GL_TRIANGLE_FAN) {
for (int i=0; i<4; i++) { // just 1 Quad
ind_line[k++] = i+0; ind_line[k++] = (i+1)%4; for (int i=0; i<4; i++) {
ind_line[k++] = i+0; ind_line[k++] = (i+1)%4;
}
} else {
// list of triangles, 2 per quads...
for (int i=0; i<len-5; i+=6) {
ind_line[k++] = i+0; ind_line[k++] = i+1;
ind_line[k++] = i+1; ind_line[k++] = i+2;
ind_line[k++] = i+2; ind_line[k++] = i+5;
ind_line[k++] = i+5; ind_line[k++] = i+0;
}
} }
} else {
// cannot go there!
} }
break; break;
case GL_QUAD_STRIP: case GL_QUAD_STRIP:
// first 4 points is a quad, then 2 points per new quad if(len>3) {
if (len>2) { // first 4 points is a quad, then 2 points per new quad
ind_line[k++] = 0; ind_line[k++] = 1; if (len>2) {
} ind_line[k++] = 0; ind_line[k++] = 1;
for (int i = 2; i<len; i+=2) { }
ind_line[k++] = i-1; ind_line[k++] = i; for (int i = 2; i<len-1; i+=2) {
ind_line[k++] = i-2; ind_line[k++] = i+1; ind_line[k++] = i-1; ind_line[k++] = i;
ind_line[k++] = i+0; ind_line[k++] = i+1; ind_line[k++] = i-2; ind_line[k++] = i+1;
ind_line[k++] = i+0; ind_line[k++] = i+1;
}
} }
break; break;
case GL_POLYGON: case GL_POLYGON:
// if polygons have been merged, then info is lost... // if polygons have been merged, then info is lost...
if (len) { if (len) {
ind_line[k++] = 0; ind_line[k++] = 1; ind_line[k++] = 0; ind_line[k++] = 1;
} for (int i = 1; i<len; i++) {
for (int i = 1; i<len; i++) { ind_line[k++] = i-1; ind_line[k++] = i;
ind_line[k++] = i-1; ind_line[k++] = i; }
}
if (len) {
ind_line[k++] = len-1; ind_line[k++] = 0; ind_line[k++] = len-1; ind_line[k++] = 0;
} }
break; break;
@@ -1212,10 +1218,7 @@ void rlTexGenfv(renderlist_t *list, GLenum coord, GLenum pname, const GLfloat *
m->coord = coord; m->coord = coord;
m->pname = pname; m->pname = pname;
m->color[0] = params[0]; memcpy(m->color, params, 4*sizeof(GLfloat));
m->color[1] = params[1];
m->color[2] = params[2];
m->color[3] = params[3];
} }
void rlTexCoord2f(renderlist_t *list, GLfloat s, GLfloat t) { void rlTexCoord2f(renderlist_t *list, GLfloat s, GLfloat t) {

View File

@@ -575,7 +575,7 @@ bool pixel_convert(const GLvoid *src, GLvoid **dst,
const colorlayout_t *src_color, *dst_color; const colorlayout_t *src_color, *dst_color;
GLuint pixels = width * height; GLuint pixels = width * height;
GLuint dst_size = pixels * pixel_sizeof(dst_format, dst_type); GLuint dst_size = pixels * pixel_sizeof(dst_format, dst_type);
GLuint dst_width = stride * pixel_sizeof(dst_format, dst_type); GLuint dst_width = ((stride?stride:width) - width) * pixel_sizeof(dst_format, dst_type);
GLuint src_width = width * pixel_sizeof(dst_format, dst_type); GLuint src_width = width * pixel_sizeof(dst_format, dst_type);
//printf("pixel conversion: %ix%i - %04x, %04x -> %04x, %04x, transform=%i\n", width, height, src_format, src_type, dst_format, dst_type, raster_need_transform()); //printf("pixel conversion: %ix%i - %04x, %04x -> %04x, %04x, transform=%i\n", width, height, src_format, src_type, dst_format, dst_type, raster_need_transform());
@@ -592,7 +592,7 @@ bool pixel_convert(const GLvoid *src, GLvoid **dst,
*dst = malloc(dst_size); *dst = malloc(dst_size);
if (stride) // for in-place conversion if (stride) // for in-place conversion
for (int yy=0; yy<height; yy++) for (int yy=0; yy<height; yy++)
memcpy((*dst)+yy*dst_width, src+yy*src_width, src_width); memcpy((*dst)+yy*(dst_width+src_width), src+yy*src_width, src_width);
else else
memcpy(*dst, src, dst_size); memcpy(*dst, src, dst_size);
return true; return true;
@@ -614,7 +614,7 @@ bool pixel_convert(const GLvoid *src, GLvoid **dst,
dst_pos += dst_stride; dst_pos += dst_stride;
} }
if (stride) if (stride)
dst_pos += dst_width - src_width; dst_pos += dst_width;
} }
return true; return true;
} }
@@ -628,7 +628,7 @@ bool pixel_convert(const GLvoid *src, GLvoid **dst,
dst_pos += dst_stride; dst_pos += dst_stride;
} }
if (stride) if (stride)
dst_pos += dst_width - src_width; dst_pos += dst_width;
} }
return true; return true;
} }
@@ -642,7 +642,7 @@ bool pixel_convert(const GLvoid *src, GLvoid **dst,
dst_pos += dst_stride; dst_pos += dst_stride;
} }
if (stride) if (stride)
dst_pos += dst_width - src_width; dst_pos += dst_width;
} }
return true; return true;
} }
@@ -659,7 +659,7 @@ bool pixel_convert(const GLvoid *src, GLvoid **dst,
dst_pos += dst_stride; dst_pos += dst_stride;
} }
if (stride) if (stride)
dst_pos += dst_width - src_width; dst_pos += dst_width;
} }
return true; return true;
} }

View File

@@ -224,8 +224,9 @@ void glPushAttrib(GLbitfield mask) {
int a; int a;
for (a=0; a<MAX_TEX; a++) { for (a=0; a<MAX_TEX; a++) {
cur->texgen_r[a] = state.enable.texgen_r[a]; cur->texgen_r[a] = state.enable.texgen_r[a];
cur->texgen_r[a] = state.enable.texgen_s[a]; cur->texgen_s[a] = state.enable.texgen_s[a];
cur->texgen_r[a] = state.enable.texgen_t[a]; cur->texgen_t[a] = state.enable.texgen_t[a];
cur->texgen[a] = state.texgen[a]; // all mode and planes per texture in 1 line
cur->texture[a] = (state.texture.bound[a])?state.texture.bound[a]->texture:0; cur->texture[a] = (state.texture.bound[a])?state.texture.bound[a]->texture:0;
} }
//glActiveTexture(GL_TEXTURE0+cur->active); //glActiveTexture(GL_TEXTURE0+cur->active);
@@ -478,6 +479,7 @@ void glPopAttrib() {
state.enable.texgen_r[a] = cur->texgen_r[a]; state.enable.texgen_r[a] = cur->texgen_r[a];
state.enable.texgen_s[a] = cur->texgen_s[a]; state.enable.texgen_s[a] = cur->texgen_s[a];
state.enable.texgen_t[a] = cur->texgen_t[a]; state.enable.texgen_t[a] = cur->texgen_t[a];
state.texgen[a] = cur->texgen[a]; // all mode and planes per texture in 1 line
if ((cur->texture[a]==0 && state.texture.bound[a] != 0) || (cur->texture[a]!=0 && state.texture.bound[a]==0)) { if ((cur->texture[a]==0 && state.texture.bound[a] != 0) || (cur->texture[a]!=0 && state.texture.bound[a]==0)) {
glActiveTexture(GL_TEXTURE0+a); glActiveTexture(GL_TEXTURE0+a);
glBindTexture(GL_TEXTURE_2D, cur->texture[a]); glBindTexture(GL_TEXTURE_2D, cur->texture[a]);

View File

@@ -118,6 +118,7 @@ typedef struct {
// GL_TEXTURE_BIT // GL_TEXTURE_BIT
GLint texture[MAX_TEX]; GLint texture[MAX_TEX];
texgen_state_t texgen[MAX_TEX];
GLint active; GLint active;
// GL_TRANSFORM_BIT // GL_TRANSFORM_BIT
@@ -159,18 +160,6 @@ typedef struct {
GLboolean normal_enable; GLboolean normal_enable;
GLboolean secondary_enable; GLboolean secondary_enable;
pointer_states_t pointers; pointer_states_t pointers;
/*pointer_state_t verts;
pointer_state_t color;
pointer_state_t normal;
pointer_state_t tex[MAX_TEX];
pointer_state_t secondary;*/
// lets track old pointer address to avoid useless copy back
/*GLvoid *ref_verts,
*ref_colors,
*ref_secondary,
*ref_normal,
*ref_tex[MAX_TEX];
*/
unsigned int len; unsigned int len;
unsigned int cap; unsigned int cap;
} glclientstack_t; } glclientstack_t;

View File

@@ -9,6 +9,7 @@
typedef struct { typedef struct {
GLboolean line_stipple, GLboolean line_stipple,
auto_normal,
blend, blend,
color_sum, color_sum,
secondary_array, secondary_array,
@@ -29,9 +30,12 @@ typedef struct {
GLenum S; GLenum S;
GLenum T; GLenum T;
GLenum R; GLenum R;
GLfloat Sv[4]; GLfloat S_E[4]; // Eye Plane
GLfloat Tv[4]; GLfloat T_E[4];
GLfloat Rv[4]; GLfloat R_E[4];
GLfloat S_O[4]; // Object Plane
GLfloat T_O[4];
GLfloat R_O[4];
} texgen_state_t; } texgen_state_t;
typedef struct { typedef struct {

View File

@@ -3,25 +3,23 @@
//extern void* eglGetProcAddress(const char*); //extern void* eglGetProcAddress(const char*);
void glTexGeni(GLenum coord, GLenum pname, GLint param) { void glTexGeni(GLenum coord, GLenum pname, GLint param) {
// coord is in: GL_S, GL_T, GL_R, GL_Q
// pname == GL_TEXTURE_GEN_MODE
/* param is in:
GL_OBJECT_LINEAR, GL_EYE_LINEAR,
GL_SPHERE_MAP, GL_NORMAL_MAP, or GL_REFLECTION_MAP
*/
/*
switch (coord) {
case GL_S: state.texgen[state.texture.active].S = param; break;
case GL_T: state.texgen[state.texture.active].T = param; break;
}
*/
GLfloat params[4] = {0,0,0,0}; GLfloat params[4] = {0,0,0,0};
params[0]=param; params[0]=param;
glTexGenfv(coord, pname, params); glTexGenfv(coord, pname, params);
} }
void glTexGenfv(GLenum coord, GLenum pname, const GLfloat *param) { void glTexGenfv(GLenum coord, GLenum pname, const GLfloat *param) {
//printf("glTexGenfv(0x%04X, 0x%04X, [%.02f, ...]), texture=%i\n", coord, pname, param[0], state.texture.active);
/*
If pname is GL_TEXTURE_GEN_MODE, then the array must contain
a single symbolic constant, one of
GL_OBJECT_LINEAR, GL_EYE_LINEAR, GL_SPHERE_MAP, GL_NORMAL_MAP,
or GL_REFLECTION_MAP.
Otherwise, params holds the coefficients for the texture-coordinate
generation function specified by pname.
*/
//printf("glTexGenfv(0x%04X, 0x%04X, [%.02f, ...]), texture=%i\n", coord, pname, param[0], state.texture.active);
if ((state.list.compiling || state.gl_batch) && state.list.active) { if ((state.list.compiling || state.gl_batch) && state.list.active) {
NewStage(state.list.active, STAGE_TEXGEN); NewStage(state.list.active, STAGE_TEXGEN);
rlTexGenfv(state.list.active, coord, pname, param); rlTexGenfv(state.list.active, coord, pname, param);
@@ -31,38 +29,49 @@ void glTexGenfv(GLenum coord, GLenum pname, const GLfloat *param) {
// pname is in: GL_TEXTURE_GEN_MODE, GL_OBJECT_PLANE, GL_EYE_PLANE // pname is in: GL_TEXTURE_GEN_MODE, GL_OBJECT_PLANE, GL_EYE_PLANE
noerrorShim(); noerrorShim();
if (pname == GL_TEXTURE_GEN_MODE) { switch(pname) {
switch (coord) { case GL_TEXTURE_GEN_MODE:
case GL_S: state.texgen[state.texture.active].S = param[0]; break; switch (coord) {
case GL_T: state.texgen[state.texture.active].T = param[0]; break; case GL_S: state.texgen[state.texture.active].S = param[0]; break;
case GL_R: state.texgen[state.texture.active].R = param[0]; break; case GL_T: state.texgen[state.texture.active].T = param[0]; break;
default: case GL_R: state.texgen[state.texture.active].R = param[0]; break;
errorShim(GL_INVALID_ENUM); default:
} errorShim(GL_INVALID_ENUM);
} else { return;
switch (coord) { }
case GL_S: case GL_OBJECT_PLANE:
memcpy(state.texgen[state.texture.active].Sv, param, 4 * sizeof(GLfloat)); switch (coord) {
break; case GL_S:
case GL_T: memcpy(state.texgen[state.texture.active].S_O, param, 4 * sizeof(GLfloat));
memcpy(state.texgen[state.texture.active].Tv, param, 4 * sizeof(GLfloat)); break;
break; case GL_T:
case GL_R: memcpy(state.texgen[state.texture.active].T_O, param, 4 * sizeof(GLfloat));
memcpy(state.texgen[state.texture.active].Rv, param, 4 * sizeof(GLfloat)); break;
break; case GL_R:
default: memcpy(state.texgen[state.texture.active].R_O, param, 4 * sizeof(GLfloat));
errorShim(GL_INVALID_ENUM); break;
} default:
errorShim(GL_INVALID_ENUM);
return;
}
case GL_EYE_PLANE:
switch (coord) {
case GL_S:
memcpy(state.texgen[state.texture.active].S_E, param, 4 * sizeof(GLfloat));
break;
case GL_T:
memcpy(state.texgen[state.texture.active].T_E, param, 4 * sizeof(GLfloat));
break;
case GL_R:
memcpy(state.texgen[state.texture.active].R_E, param, 4 * sizeof(GLfloat));
break;
default:
errorShim(GL_INVALID_ENUM);
return;
}
default:
errorShim(GL_INVALID_ENUM);
} }
/*
If pname is GL_TEXTURE_GEN_MODE, then the array must contain
a single symbolic constant, one of
GL_OBJECT_LINEAR, GL_EYE_LINEAR, GL_SPHERE_MAP, GL_NORMAL_MAP,
or GL_REFLECTION_MAP.
Otherwise, params holds the coefficients for the texture-coordinate
generation function specified by pname.
*/
} }
void glGetTexGenfv(GLenum coord,GLenum pname,GLfloat *params) { void glGetTexGenfv(GLenum coord,GLenum pname,GLfloat *params) {
if (gl_batch) flush(); if (gl_batch) flush();
@@ -77,16 +86,29 @@ void glGetTexGenfv(GLenum coord,GLenum pname,GLfloat *params) {
} }
break; break;
case GL_OBJECT_PLANE: case GL_OBJECT_PLANE:
case GL_EYE_PLANE: // probably wrong...
switch (coord) { switch (coord) {
case GL_S: case GL_S:
memcpy(params, state.texgen[state.texture.active].Sv, 4 * sizeof(GLfloat)); memcpy(params, state.texgen[state.texture.active].S_O, 4 * sizeof(GLfloat));
break; break;
case GL_T: case GL_T:
memcpy(params, state.texgen[state.texture.active].Tv, 4 * sizeof(GLfloat)); memcpy(params, state.texgen[state.texture.active].T_O, 4 * sizeof(GLfloat));
break; break;
case GL_R: case GL_R:
memcpy(params, state.texgen[state.texture.active].Rv, 4 * sizeof(GLfloat)); memcpy(params, state.texgen[state.texture.active].R_O, 4 * sizeof(GLfloat));
break;
default:
errorShim(GL_INVALID_ENUM);
}
case GL_EYE_PLANE:
switch (coord) {
case GL_S:
memcpy(params, state.texgen[state.texture.active].S_E, 4 * sizeof(GLfloat));
break;
case GL_T:
memcpy(params, state.texgen[state.texture.active].T_E, 4 * sizeof(GLfloat));
break;
case GL_R:
memcpy(params, state.texgen[state.texture.active].R_E, 4 * sizeof(GLfloat));
break; break;
default: default:
errorShim(GL_INVALID_ENUM); errorShim(GL_INVALID_ENUM);
@@ -261,13 +283,13 @@ void eye_loop(const GLfloat *verts, const GLfloat *param, GLfloat *out, GLint co
} }
static inline void tex_coord_loop(GLfloat *verts, GLfloat *norm, GLfloat *out, GLint count, GLenum type, GLfloat *params, GLushort *indices) { static inline void tex_coord_loop(GLfloat *verts, GLfloat *norm, GLfloat *out, GLint count, GLenum type, GLfloat *param_o, GLfloat *param_e, GLushort *indices) {
switch (type) { switch (type) {
case GL_OBJECT_LINEAR: case GL_OBJECT_LINEAR:
dot_loop(verts, params, out, count, indices); dot_loop(verts, param_o, out, count, indices);
break; break;
case GL_EYE_LINEAR: case GL_EYE_LINEAR:
eye_loop(verts, params, out, count, indices); eye_loop(verts, param_e, out, count, indices);
break; break;
case GL_SPHERE_MAP: case GL_SPHERE_MAP:
//printf("LIBGL: GL_SPHERE_MAP with only 1 TexGen available"); //Broken here //printf("LIBGL: GL_SPHERE_MAP with only 1 TexGen available"); //Broken here
@@ -352,30 +374,10 @@ void gen_tex_coords(GLfloat *verts, GLfloat *norm, GLfloat **coords, GLint count
return; return;
if ((*coords)==NULL) if ((*coords)==NULL)
*coords = (GLfloat *)malloc(count * 2 * sizeof(GLfloat)); *coords = (GLfloat *)malloc(count * 2 * sizeof(GLfloat));
/* LOAD_GLES(glPushMatrix);
LOAD_GLES(glGetIntegerv);
LOAD_GLES(glMatrixMode);
LOAD_GLES(glLoadIdentity);
LOAD_GLES(glActiveTexture);
GLuint old=state.texture.active;
GLuint matmode;
gles_glGetIntegerv(GL_MATRIX_MODE, &matmode);
if (matmode!=GL_TEXTURE)
gles_glMatrixMode(GL_TEXTURE);
if (old!=texture)
gles_glActiveTexture(GL_TEXTURE0+texture);
gles_glPushMatrix();
gles_glLoadIdentity();
if (matmode!=GL_TEXTURE)
gles_glMatrixMode(matmode);
if (old!=texture)
gles_glActiveTexture(GL_TEXTURE0+old);
*needclean=2;
*/
if (state.enable.texgen_s[texture]) if (state.enable.texgen_s[texture])
tex_coord_loop(verts, norm, *coords, (indices)?ilen:count, state.texgen[texture].S, state.texgen[texture].Sv, indices); tex_coord_loop(verts, norm, *coords, (indices)?ilen:count, state.texgen[texture].S, state.texgen[texture].S_O, state.texgen[texture].S_E, indices);
if (state.enable.texgen_t[texture]) if (state.enable.texgen_t[texture])
tex_coord_loop(verts, norm, *coords+1, (indices)?ilen:count, state.texgen[texture].T, state.texgen[texture].Tv, indices); tex_coord_loop(verts, norm, *coords+1, (indices)?ilen:count, state.texgen[texture].T, state.texgen[texture].T_O, state.texgen[texture].T_E, indices);
} }
void gen_tex_clean(GLint cleancode, int texture) { void gen_tex_clean(GLint cleancode, int texture) {
@@ -389,24 +391,6 @@ void gen_tex_clean(GLint cleancode, int texture) {
if (old_tex!=texture) glActiveTexture(GL_TEXTURE0 + old_tex); if (old_tex!=texture) glActiveTexture(GL_TEXTURE0 + old_tex);
return; return;
} }
/* if (cleancode == 2) {
LOAD_GLES(glPopMatrix);
LOAD_GLES(glGetIntegerv);
LOAD_GLES(glMatrixMode);
LOAD_GLES(glActiveTexture);
GLuint old=state.texture.active;
GLuint matmode;
gles_glGetIntegerv(GL_MATRIX_MODE, &matmode);
if (matmode!=GL_TEXTURE)
gles_glMatrixMode(GL_TEXTURE);
if (old!=texture)
gles_glActiveTexture(GL_TEXTURE0+texture);
gles_glPopMatrix();
if (matmode!=GL_TEXTURE)
gles_glMatrixMode(matmode);
if (old!=texture)
gles_glActiveTexture(GL_TEXTURE0+old);
}*/
} }
void glLoadTransposeMatrixf(const GLfloat *m) { void glLoadTransposeMatrixf(const GLfloat *m) {

View File

@@ -1,6 +1,7 @@
#include "texture.h" #include "texture.h"
#include "raster.h" #include "raster.h"
#include "decompress.h" #include "decompress.h"
#include "debug.h"
#include <EGL/egl.h> #include <EGL/egl.h>
#include <EGL/eglext.h> #include <EGL/eglext.h>
#include "../glx/streaming.h" #include "../glx/streaming.h"
@@ -99,6 +100,8 @@ void tex_setup_texcoord(GLuint texunit, GLuint len) {
if (old!=texunit) glClientActiveTexture(old+GL_TEXTURE0); if (old!=texunit) glClientActiveTexture(old+GL_TEXTURE0);
} }
int nolumalpha = 0;
static void *swizzle_texture(GLsizei width, GLsizei height, static void *swizzle_texture(GLsizei width, GLsizei height,
GLenum *format, GLenum *type, GLenum *format, GLenum *type,
const GLvoid *data) { const GLvoid *data) {
@@ -112,7 +115,10 @@ static void *swizzle_texture(GLsizei width, GLsizei height,
break; break;
case GL_ALPHA: case GL_ALPHA:
case GL_RGBA: case GL_RGBA:
break;
case GL_LUMINANCE_ALPHA: case GL_LUMINANCE_ALPHA:
if(nolumalpha)
convert = true;
break; break;
case GL_RGB5: case GL_RGB5:
dest_type = GL_UNSIGNED_SHORT_5_6_5; dest_type = GL_UNSIGNED_SHORT_5_6_5;
@@ -197,7 +203,7 @@ void glTexImage2D(GLenum target, GLint level, GLint internalformat,
GLsizei width, GLsizei height, GLint border, GLsizei width, GLsizei height, GLint border,
GLenum format, GLenum type, const GLvoid *data) { GLenum format, GLenum type, const GLvoid *data) {
//printf("glTexImage2D on target=0x%04X with unpack_row_length(%i), size(%i,%i) and skip(%i,%i), format(internal)=%04x(%04x), type=%04x, data=%08x, level=%i (mipmap_need=%i, mipmap_auto=%i) => texture=%u (streamed=%i)\n", target, state.texture.unpack_row_length, width, height, state.texture.unpack_skip_pixels, state.texture.unpack_skip_rows, format, internalformat, type, data, level, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->mipmap_need:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->mipmap_auto:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->texture:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->streamed:0); //printf("glTexImage2D on target=%s with unpack_row_length(%i), size(%i,%i) and skip(%i,%i), format(internal)=%s(%s), type=%s, data=%08x, level=%i (mipmap_need=%i, mipmap_auto=%i) => texture=%u (streamed=%i)\n", PrintEnum(target), state.texture.unpack_row_length, width, height, state.texture.unpack_skip_pixels, state.texture.unpack_skip_rows, PrintEnum(format), PrintEnum(internalformat), PrintEnum(type), data, level, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->mipmap_need:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->mipmap_auto:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->texture:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->streamed:0);
// proxy case // proxy case
if (target == GL_PROXY_TEXTURE_2D) { if (target == GL_PROXY_TEXTURE_2D) {
@@ -301,6 +307,11 @@ void glTexImage2D(GLenum target, GLint level, GLint internalformat,
printf("LIBGL: No glCopyTexImage2D / glCopyTexSubImage2D hack\n"); printf("LIBGL: No glCopyTexImage2D / glCopyTexSubImage2D hack\n");
copytex = 1; copytex = 1;
} }
char *env_lumalpha = getenv("LIBGL_NOLUMALPHA");
if (env_lumalpha && strcmp(env_lumalpha, "1") == 0) {
nolumalpha = 1;
printf("LIBGL: GL_LUMINANCE_ALPHA hardware support disabled\n");
}
tested_env = true; tested_env = true;
} }
@@ -582,7 +593,7 @@ void glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset,
LOAD_GLES(glTexSubImage2D); LOAD_GLES(glTexSubImage2D);
LOAD_GLES(glTexParameteri); LOAD_GLES(glTexParameteri);
noerrorShim(); noerrorShim();
//printf("glTexSubImage2D on target=0x%04X with unpack_row_length(%i), size(%i,%i), pos(%i,%i) and skip={%i,%i}, format=%04x, type=%04x, level=%i, texture=%u\n", target, state.texture.unpack_row_length, width, height, xoffset, yoffset, state.texture.unpack_skip_pixels, state.texture.unpack_skip_rows, format, type, level, state.texture.bound[state.texture.active]->texture); //printf("glTexSubImage2D on target=%s with unpack_row_length(%i), size(%i,%i), pos(%i,%i) and skip={%i,%i}, format=%s, type=%s, level=%i, texture=%u\n", PrintEnum(target), state.texture.unpack_row_length, width, height, xoffset, yoffset, state.texture.unpack_skip_pixels, state.texture.unpack_skip_rows, PrintEnum(format), PrintEnum(type), level, state.texture.bound[state.texture.active]->texture);
if (width==0 || height==0) { if (width==0 || height==0) {
state.gl_batch = old_glbatch; state.gl_batch = old_glbatch;
return; return;
@@ -696,7 +707,7 @@ void glTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset,
gles_glTexParameteri( target, GL_GENERATE_MIPMAP, GL_FALSE ); gles_glTexParameteri( target, GL_GENERATE_MIPMAP, GL_FALSE );
if ((target==GL_TEXTURE_2D) && texcopydata && bound && ((texstream && !bound->streamed) || !texstream)) { if ((target==GL_TEXTURE_2D) && texcopydata && bound && ((texstream && !bound->streamed) || !texstream)) {
//printf("*texcopy* glTexSubImage2D, xy=%i,%i, size=%i,%i, format=0x%04X, type=0x%04X, tex=%u\n", xoffset, yoffset, width, height, format, type, bound->glname); //printf("*texcopy* glTexSubImage2D, xy=%i,%i, size=%i,%i=>%i,%i, format=%s, type=%s, tex=%u\n", xoffset, yoffset, width, height, bound->width, bound->height, PrintEnum(format), PrintEnum(type), bound->glname);
GLvoid * tmp = bound->data; GLvoid * tmp = bound->data;
tmp += (yoffset*bound->width + xoffset)*4; tmp += (yoffset*bound->width + xoffset)*4;
if (!pixel_convert(pixels, &tmp, width, height, format, type, GL_RGBA, GL_UNSIGNED_BYTE, bound->width)) if (!pixel_convert(pixels, &tmp, width, height, format, type, GL_RGBA, GL_UNSIGNED_BYTE, bound->width))
@@ -835,7 +846,7 @@ void glBindTexture(GLenum target, GLuint texture) {
int tex_changed = 1; int tex_changed = 1;
int streamingID = -1; int streamingID = -1;
gltexture_t *tex = NULL; gltexture_t *tex = NULL;
//printf("glBindTexture(0x%04X, %u), active=%i, client=%i\n", target, texture, state.texture.active, state.texture.client); //printf("glBindTexture(0x%04X, %u), active=%i, client=%i\n", target, texture, state.texture.active, state.texture.client);
if (texture) { if (texture) {
int ret; int ret;
khint_t k; khint_t k;
@@ -1162,7 +1173,7 @@ void glGetTexImage(GLenum target, GLint level, GLenum format, GLenum type, GLvoi
gltexture_t* bound = state.texture.bound[state.texture.active]; gltexture_t* bound = state.texture.bound[state.texture.active];
int width = bound->width; int width = bound->width;
int height = bound->height; int height = bound->height;
//printf("glGetTexImage(0x%04X, %i, 0x%04X, 0x%04X, 0x%p), texture=%u, size=%i,%i\n", target, level, format, type, img, bound->glname, width, height); //printf("glGetTexImage(0x%04X, %i, 0x%04X, 0x%04X, 0x%p), texture=%u, size=%i,%i\n", target, level, format, type, img, bound->glname, width, height);
GLvoid *dst = img; GLvoid *dst = img;
if (state.buffers.pack) if (state.buffers.pack)
@@ -1176,7 +1187,8 @@ void glGetTexImage(GLenum target, GLint level, GLenum format, GLenum type, GLvoi
} }
#endif #endif
if (texcopydata && bound->data) { if (texcopydata && bound->data) {
errorShim(GL_INVALID_ENUM); printf("texcopydata* glGetTexImage(0x%04X, %d, 0x%04x, 0x%04X, %p)\n", target, level, format, type, img);
noerrorShim();
if (!pixel_convert(bound->data, &dst, width, height, GL_RGBA, GL_UNSIGNED_BYTE, format, type, 0)) if (!pixel_convert(bound->data, &dst, width, height, GL_RGBA, GL_UNSIGNED_BYTE, format, type, 0))
printf("LIBGL: Error on pixel_convert while glGetTexImage\n"); printf("LIBGL: Error on pixel_convert while glGetTexImage\n");
} else { } else {
@@ -1275,7 +1287,7 @@ void glReadPixels(GLint x, GLint y, GLsizei width, GLsizei height, GLenum format
void glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset, void glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffset,
GLint x, GLint y, GLsizei width, GLsizei height) { GLint x, GLint y, GLsizei width, GLsizei height) {
//printf("glCopyTexSubImage2D(%i, %i, %i, %i, %i, %i, %i, %i), bounded texture=%u format/type=0x%04X, 0x%04X\n", target, level, xoffset, yoffset, x, y, width, height, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->texture:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->format:0, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->type:0); //printf("glCopyTexSubImage2D(%s, %i, %i, %i, %i, %i, %i, %i), bounded texture=%u format/type=%s, %s\n", PrintEnum(target), level, xoffset, yoffset, x, y, width, height, (state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->texture:0, PrintEnum((state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->format:0), PrintEnum((state.texture.bound[state.texture.active])?state.texture.bound[state.texture.active]->type:0));
// PUSH_IF_COMPILING(glCopyTexSubImage2D); // PUSH_IF_COMPILING(glCopyTexSubImage2D);
GLuint old_glbatch = state.gl_batch; GLuint old_glbatch = state.gl_batch;
if (state.gl_batch) { if (state.gl_batch) {
@@ -1334,7 +1346,7 @@ void glCopyTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint yoffse
void glCopyTexImage2D(GLenum target, GLint level, GLenum internalformat, GLint x, GLint y, void glCopyTexImage2D(GLenum target, GLint level, GLenum internalformat, GLint x, GLint y,
GLsizei width, GLsizei height, GLint border) { GLsizei width, GLsizei height, GLint border) {
//printf("glCopyTexImage2D(0x%04X, %i, 0x%04X, %i, %i, %i, %i, %i), current_fb=%u\n", target, level, internalformat, x, y, width, height, border, current_fb); //printf("glCopyTexImage2D(0x%04X, %i, 0x%04X, %i, %i, %i, %i, %i), current_fb=%u\n", target, level, internalformat, x, y, width, height, border, current_fb);
//PUSH_IF_COMPILING(glCopyTexImage2D); //PUSH_IF_COMPILING(glCopyTexImage2D);
GLuint old_glbatch = state.gl_batch; GLuint old_glbatch = state.gl_batch;
if (state.gl_batch) { if (state.gl_batch) {
@@ -1558,7 +1570,7 @@ void glCompressedTexSubImage2D(GLenum target, GLint level, GLint xoffset, GLint
state.gl_batch = old_glbatch; state.gl_batch = old_glbatch;
return; return;
} }
//printf("glCompressedTexSubImage2D with unpack_row_length(%i), size(%i,%i), pos(%i,%i) and skip={%i,%i}, internalformat=%04x, imagesize=%i\n", state.texture.unpack_row_length, width, height, xoffset, yoffset, state.texture.unpack_skip_pixels, state.texture.unpack_skip_rows, format, imageSize); //printf("glCompressedTexSubImage2D with unpack_row_length(%i), size(%i,%i), pos(%i,%i) and skip={%i,%i}, internalformat=%s, imagesize=%i\n", state.texture.unpack_row_length, width, height, xoffset, yoffset, state.texture.unpack_skip_pixels, state.texture.unpack_skip_rows, PrintEnum(format), imageSize);
glbuffer_t *unpack = state.buffers.unpack; glbuffer_t *unpack = state.buffers.unpack;
state.buffers.unpack = NULL; state.buffers.unpack = NULL;
GLvoid *datab = (GLvoid*)data; GLvoid *datab = (GLvoid*)data;

View File

@@ -678,11 +678,12 @@ void glTexCoord4fv(GLfloat *t) {
// texgen // texgen
void glTexGend(GLenum coord, GLenum pname, GLdouble param) { void glTexGend(GLenum coord, GLenum pname, GLdouble param) {
glTexGeni(coord, pname, param); glTexGenf(coord, pname, param);
} }
void glTexGenf(GLenum coord, GLenum pname, GLfloat param) { void glTexGenf(GLenum coord, GLenum pname, GLfloat param) {
// TODO: this is gross/lossy. GLfloat params[4] = {0,0,0,0};
glTexGeni(coord, pname, param); params[0] = param;
glTexGenfv(coord, pname, params);
} }
void glTexGendv(GLenum coord, GLenum pname, const GLdouble *params) { void glTexGendv(GLenum coord, GLenum pname, const GLdouble *params) {
GLfloat tmp[4]; GLfloat tmp[4];

View File

@@ -156,6 +156,7 @@ static bool g_usefbo = false;
static bool g_xrefresh = false; static bool g_xrefresh = false;
static bool g_stacktrace = false; static bool g_stacktrace = false;
static bool g_bcm_active = false; static bool g_bcm_active = false;
bool g_recyclefbo = false;
static int g_width=0, g_height=0; static int g_width=0, g_height=0;
#ifndef BCMHOST #ifndef BCMHOST
static bool g_bcmhost = false; static bool g_bcmhost = false;
@@ -303,6 +304,7 @@ static void scan_env() {
printf("LIBGL: LiveInfo detected, fps will be shown\n"); printf("LIBGL: LiveInfo detected, fps will be shown\n");
} }
#endif #endif
env(LIBGL_RECYCLEFBO, g_recyclefbo, "Recycling of FBO enabled");
char cwd[1024]; char cwd[1024];
if (getcwd(cwd, sizeof(cwd))!= NULL) if (getcwd(cwd, sizeof(cwd))!= NULL)
printf("LIBGL: Current folder is:%s\n", cwd); printf("LIBGL: Current folder is:%s\n", cwd);