Huge refactor of internal state
This commit is contained in:
parent
8beb295c6b
commit
8789d6557e
226
GL/draw.c
226
GL/draw.c
|
@ -997,40 +997,140 @@ GL_FORCE_INLINE void divide(SubmissionTarget* target) {
|
|||
}
|
||||
}
|
||||
|
||||
GL_FORCE_INLINE int _calc_pvr_face_culling() {
|
||||
if(!_glIsCullingEnabled()) {
|
||||
return GPU_CULLING_SMALL;
|
||||
} else {
|
||||
if(_glGetCullFace() == GL_BACK) {
|
||||
return (_glGetFrontFace() == GL_CW) ? GPU_CULLING_CCW : GPU_CULLING_CW;
|
||||
} else {
|
||||
return (_glGetFrontFace() == GL_CCW) ? GPU_CULLING_CCW : GPU_CULLING_CW;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
GL_FORCE_INLINE int _calc_pvr_depth_test() {
|
||||
if(!_glIsDepthTestEnabled()) {
|
||||
return GPU_DEPTHCMP_ALWAYS;
|
||||
}
|
||||
|
||||
switch(_glGetDepthFunc()) {
|
||||
case GL_NEVER:
|
||||
return GPU_DEPTHCMP_NEVER;
|
||||
case GL_LESS:
|
||||
return GPU_DEPTHCMP_GREATER;
|
||||
case GL_EQUAL:
|
||||
return GPU_DEPTHCMP_EQUAL;
|
||||
case GL_LEQUAL:
|
||||
return GPU_DEPTHCMP_GEQUAL;
|
||||
case GL_GREATER:
|
||||
return GPU_DEPTHCMP_LESS;
|
||||
case GL_NOTEQUAL:
|
||||
return GPU_DEPTHCMP_NOTEQUAL;
|
||||
case GL_GEQUAL:
|
||||
return GPU_DEPTHCMP_LEQUAL;
|
||||
break;
|
||||
case GL_ALWAYS:
|
||||
default:
|
||||
return GPU_DEPTHCMP_ALWAYS;
|
||||
}
|
||||
}
|
||||
|
||||
GL_FORCE_INLINE int _calcPVRBlendFactor(GLenum factor) {
|
||||
switch(factor) {
|
||||
case GL_ZERO:
|
||||
return GPU_BLEND_ZERO;
|
||||
case GL_SRC_ALPHA:
|
||||
return GPU_BLEND_SRCALPHA;
|
||||
case GL_DST_COLOR:
|
||||
return GPU_BLEND_DESTCOLOR;
|
||||
case GL_DST_ALPHA:
|
||||
return GPU_BLEND_DESTALPHA;
|
||||
case GL_ONE_MINUS_DST_COLOR:
|
||||
return GPU_BLEND_INVDESTCOLOR;
|
||||
case GL_ONE_MINUS_SRC_ALPHA:
|
||||
return GPU_BLEND_INVSRCALPHA;
|
||||
case GL_ONE_MINUS_DST_ALPHA:
|
||||
return GPU_BLEND_INVDESTALPHA;
|
||||
case GL_ONE:
|
||||
return GPU_BLEND_ONE;
|
||||
default:
|
||||
fprintf(stderr, "Invalid blend mode: %u\n", (unsigned int) factor);
|
||||
return GPU_BLEND_ONE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
GL_FORCE_INLINE void _updatePVRBlend(PolyContext* context) {
|
||||
if(_glIsBlendingEnabled() || _glIsAlphaTestEnabled()) {
|
||||
context->gen.alpha = GPU_ALPHA_ENABLE;
|
||||
} else {
|
||||
context->gen.alpha = GPU_ALPHA_DISABLE;
|
||||
}
|
||||
|
||||
context->blend.src = _calcPVRBlendFactor(_glGetBlendSourceFactor());
|
||||
context->blend.dst = _calcPVRBlendFactor(_glGetBlendDestFactor());
|
||||
}
|
||||
|
||||
GL_FORCE_INLINE void apply_poly_header(PolyHeader* header, GLboolean multiTextureHeader, PolyList* activePolyList, GLshort textureUnit) {
|
||||
TRACE();
|
||||
|
||||
// Compile the header
|
||||
PolyContext cxt = *_glGetPVRContext();
|
||||
cxt.list_type = activePolyList->list_type;
|
||||
PolyContext ctx;
|
||||
memset(&ctx, 0, sizeof(PolyContext));
|
||||
|
||||
if(cxt.list_type == GPU_LIST_OP_POLY) {
|
||||
/* Opaque polys are always one/zero */
|
||||
cxt.blend.src = GPU_BLEND_ONE;
|
||||
cxt.blend.dst = GPU_BLEND_ZERO;
|
||||
} else if(cxt.list_type == GPU_LIST_PT_POLY) {
|
||||
/* Punch-through polys require fixed blending and depth modes */
|
||||
cxt.blend.src = GPU_BLEND_SRCALPHA;
|
||||
cxt.blend.dst = GPU_BLEND_INVSRCALPHA;
|
||||
cxt.depth.comparison = GPU_DEPTHCMP_LEQUAL;
|
||||
} else if(cxt.list_type == GPU_LIST_TR_POLY && AUTOSORT_ENABLED) {
|
||||
/* Autosort mode requires this mode for transparent polys */
|
||||
cxt.depth.comparison = GPU_DEPTHCMP_GEQUAL;
|
||||
ctx.list_type = activePolyList->list_type;
|
||||
ctx.fmt.color = GPU_CLRFMT_ARGBPACKED;
|
||||
ctx.fmt.uv = GPU_UVFMT_32BIT;
|
||||
ctx.gen.color_clamp = GPU_CLRCLAMP_DISABLE;
|
||||
|
||||
ctx.gen.culling = _calc_pvr_face_culling();
|
||||
ctx.depth.comparison = _calc_pvr_depth_test();
|
||||
ctx.depth.write = _glIsDepthWriteEnabled() ? GPU_DEPTHWRITE_ENABLE : GPU_DEPTHWRITE_DISABLE;
|
||||
|
||||
ctx.gen.shading = (_glGetShadeModel() == GL_SMOOTH) ? GPU_SHADE_GOURAUD : GPU_SHADE_FLAT;
|
||||
|
||||
if(_glIsScissorTestEnabled()) {
|
||||
ctx.gen.clip_mode = GPU_USERCLIP_INSIDE;
|
||||
} else {
|
||||
ctx.gen.clip_mode = GPU_USERCLIP_DISABLE;
|
||||
}
|
||||
|
||||
_glUpdatePVRTextureContext(&cxt, textureUnit);
|
||||
if(_glIsFogEnabled()) {
|
||||
ctx.gen.fog_type = GPU_FOG_TABLE;
|
||||
} else {
|
||||
ctx.gen.fog_type = GPU_FOG_DISABLE;
|
||||
}
|
||||
|
||||
_updatePVRBlend(&ctx);
|
||||
|
||||
if(ctx.list_type == GPU_LIST_OP_POLY) {
|
||||
/* Opaque polys are always one/zero */
|
||||
ctx.blend.src = GPU_BLEND_ONE;
|
||||
ctx.blend.dst = GPU_BLEND_ZERO;
|
||||
} else if(ctx.list_type == GPU_LIST_PT_POLY) {
|
||||
/* Punch-through polys require fixed blending and depth modes */
|
||||
ctx.blend.src = GPU_BLEND_SRCALPHA;
|
||||
ctx.blend.dst = GPU_BLEND_INVSRCALPHA;
|
||||
ctx.depth.comparison = GPU_DEPTHCMP_LEQUAL;
|
||||
} else if(ctx.list_type == GPU_LIST_TR_POLY && AUTOSORT_ENABLED) {
|
||||
/* Autosort mode requires this mode for transparent polys */
|
||||
ctx.depth.comparison = GPU_DEPTHCMP_GEQUAL;
|
||||
}
|
||||
|
||||
_glUpdatePVRTextureContext(&ctx, textureUnit);
|
||||
|
||||
if(multiTextureHeader) {
|
||||
gl_assert(cxt.list_type == GPU_LIST_TR_POLY);
|
||||
gl_assert(ctx.list_type == GPU_LIST_TR_POLY);
|
||||
|
||||
cxt.gen.alpha = GPU_ALPHA_ENABLE;
|
||||
cxt.txr.alpha = GPU_TXRALPHA_ENABLE;
|
||||
cxt.blend.src = GPU_BLEND_ZERO;
|
||||
cxt.blend.dst = GPU_BLEND_DESTCOLOR;
|
||||
cxt.depth.comparison = GPU_DEPTHCMP_EQUAL;
|
||||
ctx.gen.alpha = GPU_ALPHA_ENABLE;
|
||||
ctx.txr.alpha = GPU_TXRALPHA_ENABLE;
|
||||
ctx.blend.src = GPU_BLEND_ZERO;
|
||||
ctx.blend.dst = GPU_BLEND_DESTCOLOR;
|
||||
ctx.depth.comparison = GPU_DEPTHCMP_EQUAL;
|
||||
}
|
||||
|
||||
CompilePolyHeader(header, &cxt);
|
||||
CompilePolyHeader(header, &ctx);
|
||||
|
||||
/* Force bits 18 and 19 on to switch to 6 triangle strips */
|
||||
header->cmd |= 0xC0000;
|
||||
|
@ -1110,13 +1210,16 @@ GL_FORCE_INLINE void submitVertices(GLenum mode, GLsizei first, GLuint count, GL
|
|||
return;
|
||||
}
|
||||
|
||||
GLboolean header_required = (target->output->vector.size == 0) || _glGPUStateIsDirty();
|
||||
|
||||
|
||||
// We don't handle this any further, so just make sure we never pass it down */
|
||||
gl_assert(mode != GL_POLYGON);
|
||||
|
||||
target->output = _glActivePolyList();
|
||||
target->count = (mode == GL_TRIANGLE_FAN) ? ((count - 2) * 3) : count;
|
||||
target->header_offset = target->output->vector.size;
|
||||
target->start_offset = target->header_offset + 1;
|
||||
target->start_offset = target->header_offset + (header_required);
|
||||
|
||||
gl_assert(target->count);
|
||||
|
||||
|
@ -1124,9 +1227,12 @@ GL_FORCE_INLINE void submitVertices(GLenum mode, GLsizei first, GLuint count, GL
|
|||
aligned_vector_resize(extras, target->count);
|
||||
|
||||
/* Make room for the vertices and header */
|
||||
aligned_vector_extend(&target->output->vector, target->count + 1);
|
||||
aligned_vector_extend(&target->output->vector, target->count + (header_required));
|
||||
|
||||
apply_poly_header(_glSubmissionTargetHeader(target), GL_FALSE, target->output, 0);
|
||||
if(header_required) {
|
||||
apply_poly_header(_glSubmissionTargetHeader(target), GL_FALSE, target->output, 0);
|
||||
_glGPUStateMarkClean();
|
||||
}
|
||||
|
||||
/* If we're lighting, then we need to do some work in
|
||||
* eye-space, so we only transform vertices by the modelview
|
||||
|
@ -1158,48 +1264,48 @@ GL_FORCE_INLINE void submitVertices(GLenum mode, GLsizei first, GLuint count, GL
|
|||
transform(target);
|
||||
}
|
||||
|
||||
/*
|
||||
Now, if multitexturing is enabled, we want to send exactly the same vertices again, except:
|
||||
- We want to enable blending, and send them to the TR list
|
||||
- We want to set the depth func to GL_EQUAL
|
||||
- We want to set the second texture ID
|
||||
- We want to set the uv coordinates to the passed st ones
|
||||
*/
|
||||
// /*
|
||||
// Now, if multitexturing is enabled, we want to send exactly the same vertices again, except:
|
||||
// - We want to enable blending, and send them to the TR list
|
||||
// - We want to set the depth func to GL_EQUAL
|
||||
// - We want to set the second texture ID
|
||||
// - We want to set the uv coordinates to the passed st ones
|
||||
// */
|
||||
|
||||
if(!TEXTURES_ENABLED[1]) {
|
||||
/* Multitexture actively disabled */
|
||||
return;
|
||||
}
|
||||
// if(!TEXTURES_ENABLED[1]) {
|
||||
// /* Multitexture actively disabled */
|
||||
// return;
|
||||
// }
|
||||
|
||||
TextureObject* texture1 = _glGetTexture1();
|
||||
// TextureObject* texture1 = _glGetTexture1();
|
||||
|
||||
/* Multitexture implicitly disabled */
|
||||
if(!texture1 || ((ENABLED_VERTEX_ATTRIBUTES & ST_ENABLED_FLAG) != ST_ENABLED_FLAG)) {
|
||||
/* Multitexture actively disabled */
|
||||
return;
|
||||
}
|
||||
// /* Multitexture implicitly disabled */
|
||||
// if(!texture1 || ((ENABLED_VERTEX_ATTRIBUTES & ST_ENABLED_FLAG) != ST_ENABLED_FLAG)) {
|
||||
// /* Multitexture actively disabled */
|
||||
// return;
|
||||
// }
|
||||
|
||||
/* Push back a copy of the list to the transparent poly list, including the header
|
||||
(hence the + 1)
|
||||
*/
|
||||
Vertex* vertex = aligned_vector_push_back(
|
||||
&_glTransparentPolyList()->vector, (Vertex*) _glSubmissionTargetHeader(target), target->count + 1
|
||||
);
|
||||
// /* Push back a copy of the list to the transparent poly list, including the header
|
||||
// (hence the + 1)
|
||||
// */
|
||||
// Vertex* vertex = aligned_vector_push_back(
|
||||
// &_glTransparentPolyList()->vector, (Vertex*) _glSubmissionTargetHeader(target), target->count + 1
|
||||
// );
|
||||
|
||||
gl_assert(vertex);
|
||||
// gl_assert(vertex);
|
||||
|
||||
PolyHeader* mtHeader = (PolyHeader*) vertex++;
|
||||
/* Send the buffer again to the transparent list */
|
||||
apply_poly_header(mtHeader, GL_TRUE, _glTransparentPolyList(), 1);
|
||||
// PolyHeader* mtHeader = (PolyHeader*) vertex++;
|
||||
// /* Send the buffer again to the transparent list */
|
||||
// apply_poly_header(mtHeader, GL_TRUE, _glTransparentPolyList(), 1);
|
||||
|
||||
/* Replace the UV coordinates with the ST ones */
|
||||
VertexExtra* ve = aligned_vector_at(target->extras, 0);
|
||||
ITERATE(target->count) {
|
||||
vertex->uv[0] = ve->st[0];
|
||||
vertex->uv[1] = ve->st[1];
|
||||
++vertex;
|
||||
++ve;
|
||||
}
|
||||
// /* Replace the UV coordinates with the ST ones */
|
||||
// VertexExtra* ve = aligned_vector_at(target->extras, 0);
|
||||
// ITERATE(target->count) {
|
||||
// vertex->uv[0] = ve->st[0];
|
||||
// vertex->uv[1] = ve->st[1];
|
||||
// ++vertex;
|
||||
// ++ve;
|
||||
// }
|
||||
}
|
||||
|
||||
void APIENTRY glDrawElements(GLenum mode, GLsizei count, GLenum type, const GLvoid* indices) {
|
||||
|
|
14
GL/private.h
14
GL/private.h
|
@ -306,7 +306,6 @@ Matrix4x4* _glGetModelViewMatrix();
|
|||
|
||||
void _glWipeTextureOnFramebuffers(GLuint texture);
|
||||
|
||||
PolyContext* _glGetPVRContext();
|
||||
GLubyte _glInitTextures();
|
||||
|
||||
void _glUpdatePVRTextureContext(PolyContext* context, GLshort textureUnit);
|
||||
|
@ -356,6 +355,16 @@ void _glApplyColorTable(TexturePalette *palette);
|
|||
|
||||
GLboolean _glIsBlendingEnabled();
|
||||
GLboolean _glIsAlphaTestEnabled();
|
||||
GLboolean _glIsCullingEnabled();
|
||||
GLboolean _glIsDepthTestEnabled();
|
||||
GLboolean _glIsDepthWriteEnabled();
|
||||
GLboolean _glIsScissorTestEnabled();
|
||||
GLboolean _glIsFogEnabled();
|
||||
GLenum _glGetDepthFunc();
|
||||
GLenum _glGetCullFace();
|
||||
GLenum _glGetFrontFace();
|
||||
GLenum _glGetBlendSourceFactor();
|
||||
GLenum _glGetBlendDestFactor();
|
||||
|
||||
extern PolyList OP_LIST;
|
||||
extern PolyList PT_LIST;
|
||||
|
@ -514,6 +523,9 @@ GLfloat* _glLightModelSceneAmbient();
|
|||
LightSource* _glLightAt(GLuint i);
|
||||
GLboolean _glNearZClippingEnabled();
|
||||
|
||||
GLboolean _glGPUStateIsDirty();
|
||||
void _glGPUStateMarkClean();
|
||||
|
||||
#define MAX_GLDC_TEXTURE_UNITS 2
|
||||
#define MAX_GLDC_LIGHTS 8
|
||||
|
||||
|
|
233
GL/state.c
233
GL/state.c
|
@ -4,12 +4,6 @@
|
|||
|
||||
#include "private.h"
|
||||
|
||||
static PolyContext GL_CONTEXT;
|
||||
|
||||
PolyContext *_glGetPVRContext() {
|
||||
return &GL_CONTEXT;
|
||||
}
|
||||
|
||||
|
||||
static struct {
|
||||
GLboolean is_dirty;
|
||||
|
@ -28,7 +22,10 @@ static struct {
|
|||
GLboolean shared_palette_enabled;
|
||||
GLboolean alpha_test_enabled;
|
||||
GLboolean polygon_offset_enabled;
|
||||
GLboolean normalize_enabled;;
|
||||
GLboolean normalize_enabled;
|
||||
GLboolean scissor_test_enabled;
|
||||
GLboolean fog_enabled;
|
||||
GLboolean depth_mask_enabled;
|
||||
|
||||
struct {
|
||||
GLint x;
|
||||
|
@ -53,36 +50,50 @@ static struct {
|
|||
LightSource lights[MAX_GLDC_LIGHTS];
|
||||
GLuint enabled_light_count;
|
||||
Material material;
|
||||
|
||||
GLenum shade_model;
|
||||
} GPUState = {
|
||||
GL_TRUE,
|
||||
GL_LESS,
|
||||
GL_FALSE,
|
||||
GL_BACK,
|
||||
GL_CCW,
|
||||
GL_FALSE,
|
||||
GL_FALSE,
|
||||
GL_TRUE,
|
||||
GL_FALSE,
|
||||
GL_FALSE,
|
||||
GL_FALSE,
|
||||
GL_FALSE,
|
||||
GL_FALSE,
|
||||
{0, 0, 640, 480, false},
|
||||
GL_ONE,
|
||||
GL_ZERO,
|
||||
GL_FALSE,
|
||||
0.0f,
|
||||
0.0f,
|
||||
{0.2f, 0.2f, 0.2f, 1.0f},
|
||||
GL_TRUE,
|
||||
GL_SINGLE_COLOR,
|
||||
GL_AMBIENT_AND_DIFFUSE,
|
||||
AMBIENT_MASK | DIFFUSE_MASK,
|
||||
{0},
|
||||
0,
|
||||
{0}
|
||||
.is_dirty = GL_TRUE,
|
||||
.depth_func = GL_LESS,
|
||||
.depth_test_enabled = GL_FALSE,
|
||||
.cull_face = GL_BACK,
|
||||
.front_face = GL_CCW,
|
||||
.culling_enabled = GL_FALSE,
|
||||
.color_material_enabled = GL_FALSE,
|
||||
.znear_clipping_enabled = GL_TRUE,
|
||||
.lighting_enabled = GL_FALSE,
|
||||
.shared_palette_enabled = GL_FALSE,
|
||||
.alpha_test_enabled = GL_FALSE,
|
||||
.polygon_offset_enabled = GL_FALSE,
|
||||
.normalize_enabled = GL_FALSE,
|
||||
.scissor_test_enabled = GL_FALSE,
|
||||
.fog_enabled = GL_FALSE,
|
||||
.depth_mask_enabled = GL_FALSE,
|
||||
.scissor_rect = {0, 0, 640, 480, false},
|
||||
.blend_sfactor = GL_ONE,
|
||||
.blend_dfactor = GL_ZERO,
|
||||
.blend_enabled = GL_FALSE,
|
||||
.offset_factor = 0.0f,
|
||||
.offset_units = 0.0f,
|
||||
.scene_ambient = {0.2f, 0.2f, 0.2f, 1.0f},
|
||||
.viewer_in_eye_coords = GL_TRUE,
|
||||
.color_control = GL_SINGLE_COLOR,
|
||||
.color_material_mode = GL_AMBIENT_AND_DIFFUSE,
|
||||
.color_material_mask = AMBIENT_MASK | DIFFUSE_MASK,
|
||||
.lights = {0},
|
||||
.enabled_light_count = 0,
|
||||
.material = {0},
|
||||
.shade_model = GL_SMOOTH
|
||||
};
|
||||
|
||||
void _glGPUStateMarkClean() {
|
||||
GPUState.is_dirty = GL_FALSE;
|
||||
}
|
||||
|
||||
GLboolean _glGPUStateIsDirty() {
|
||||
return GPUState.is_dirty;
|
||||
}
|
||||
|
||||
Material* _glActiveMaterial() {
|
||||
return &GPUState.material;
|
||||
}
|
||||
|
@ -96,6 +107,22 @@ void _glEnableLight(GLubyte light, GLboolean value) {
|
|||
GPUState.lights[light].isEnabled = value;
|
||||
}
|
||||
|
||||
GLboolean _glIsDepthTestEnabled() {
|
||||
return GPUState.depth_test_enabled;
|
||||
}
|
||||
|
||||
GLenum _glGetDepthFunc() {
|
||||
return GPUState.depth_func;
|
||||
}
|
||||
|
||||
GLboolean _glIsDepthWriteEnabled() {
|
||||
return GPUState.depth_mask_enabled;
|
||||
}
|
||||
|
||||
GLenum _glGetShadeModel() {
|
||||
return GPUState.shade_model;
|
||||
}
|
||||
|
||||
GLuint _glEnabledLightCount() {
|
||||
return GPUState.enabled_light_count;
|
||||
}
|
||||
|
@ -112,6 +139,26 @@ GLboolean _glIsAlphaTestEnabled() {
|
|||
return GPUState.alpha_test_enabled;
|
||||
}
|
||||
|
||||
GLboolean _glIsCullingEnabled() {
|
||||
return GPUState.culling_enabled;
|
||||
}
|
||||
|
||||
GLenum _glGetCullFace() {
|
||||
return GPUState.cull_face;
|
||||
}
|
||||
|
||||
GLenum _glGetFrontFace() {
|
||||
return GPUState.front_face;
|
||||
}
|
||||
|
||||
GLboolean _glIsFogEnabled() {
|
||||
return GPUState.fog_enabled;
|
||||
}
|
||||
|
||||
GLboolean _glIsScissorTestEnabled() {
|
||||
return GPUState.scissor_test_enabled;
|
||||
}
|
||||
|
||||
void _glRecalcEnabledLights() {
|
||||
GLubyte i;
|
||||
|
||||
|
@ -161,86 +208,19 @@ GLboolean _glNearZClippingEnabled() {
|
|||
|
||||
void _glApplyScissor(bool force);
|
||||
|
||||
static int _calc_pvr_face_culling() {
|
||||
if(!GPUState.culling_enabled) {
|
||||
return GPU_CULLING_SMALL;
|
||||
} else {
|
||||
if(GPUState.cull_face == GL_BACK) {
|
||||
return (GPUState.front_face == GL_CW) ? GPU_CULLING_CCW : GPU_CULLING_CW;
|
||||
} else {
|
||||
return (GPUState.front_face == GL_CCW) ? GPU_CULLING_CCW : GPU_CULLING_CW;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static int _calc_pvr_depth_test() {
|
||||
if(!GPUState.depth_test_enabled) {
|
||||
return GPU_DEPTHCMP_ALWAYS;
|
||||
}
|
||||
|
||||
switch(GPUState.depth_func) {
|
||||
case GL_NEVER:
|
||||
return GPU_DEPTHCMP_NEVER;
|
||||
case GL_LESS:
|
||||
return GPU_DEPTHCMP_GREATER;
|
||||
case GL_EQUAL:
|
||||
return GPU_DEPTHCMP_EQUAL;
|
||||
case GL_LEQUAL:
|
||||
return GPU_DEPTHCMP_GEQUAL;
|
||||
case GL_GREATER:
|
||||
return GPU_DEPTHCMP_LESS;
|
||||
case GL_NOTEQUAL:
|
||||
return GPU_DEPTHCMP_NOTEQUAL;
|
||||
case GL_GEQUAL:
|
||||
return GPU_DEPTHCMP_LEQUAL;
|
||||
break;
|
||||
case GL_ALWAYS:
|
||||
default:
|
||||
return GPU_DEPTHCMP_ALWAYS;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
GLboolean _glIsNormalizeEnabled() {
|
||||
return GPUState.normalize_enabled;
|
||||
}
|
||||
|
||||
static int _calcPVRBlendFactor(GLenum factor) {
|
||||
switch(factor) {
|
||||
case GL_ZERO:
|
||||
return GPU_BLEND_ZERO;
|
||||
case GL_SRC_ALPHA:
|
||||
return GPU_BLEND_SRCALPHA;
|
||||
case GL_DST_COLOR:
|
||||
return GPU_BLEND_DESTCOLOR;
|
||||
case GL_DST_ALPHA:
|
||||
return GPU_BLEND_DESTALPHA;
|
||||
case GL_ONE_MINUS_DST_COLOR:
|
||||
return GPU_BLEND_INVDESTCOLOR;
|
||||
case GL_ONE_MINUS_SRC_ALPHA:
|
||||
return GPU_BLEND_INVSRCALPHA;
|
||||
case GL_ONE_MINUS_DST_ALPHA:
|
||||
return GPU_BLEND_INVDESTALPHA;
|
||||
case GL_ONE:
|
||||
return GPU_BLEND_ONE;
|
||||
default:
|
||||
fprintf(stderr, "Invalid blend mode: %u\n", (unsigned int) factor);
|
||||
return GPU_BLEND_ONE;
|
||||
}
|
||||
GLenum _glGetBlendSourceFactor() {
|
||||
return GPUState.blend_sfactor;
|
||||
}
|
||||
|
||||
static void _updatePVRBlend(PolyContext* context) {
|
||||
if(GPUState.blend_enabled || GPUState.alpha_test_enabled) {
|
||||
context->gen.alpha = GPU_ALPHA_ENABLE;
|
||||
} else {
|
||||
context->gen.alpha = GPU_ALPHA_DISABLE;
|
||||
}
|
||||
|
||||
context->blend.src = _calcPVRBlendFactor(GPUState.blend_sfactor);
|
||||
context->blend.dst = _calcPVRBlendFactor(GPUState.blend_dfactor);
|
||||
GLenum _glGetBlendDestFactor() {
|
||||
return GPUState.blend_dfactor;
|
||||
}
|
||||
|
||||
|
||||
GLboolean _glCheckValidEnum(GLint param, GLint* values, const char* func) {
|
||||
GLubyte found = 0;
|
||||
while(*values != 0) {
|
||||
|
@ -378,13 +358,6 @@ GLboolean _glIsColorMaterialEnabled() {
|
|||
static GLfloat CLEAR_COLOUR[3];
|
||||
|
||||
void _glInitContext() {
|
||||
memset(&GL_CONTEXT, 0, sizeof(PolyContext));
|
||||
|
||||
GL_CONTEXT.list_type = GPU_LIST_OP_POLY;
|
||||
GL_CONTEXT.fmt.color = GPU_CLRFMT_ARGBPACKED;
|
||||
GL_CONTEXT.fmt.uv = GPU_UVFMT_32BIT;
|
||||
GL_CONTEXT.gen.color_clamp = GPU_CLRCLAMP_DISABLE;
|
||||
|
||||
const VideoMode* mode = GetVideoMode();
|
||||
|
||||
GPUState.scissor_rect.x = 0;
|
||||
|
@ -426,25 +399,21 @@ GLAPI void APIENTRY glEnable(GLenum cap) {
|
|||
break;
|
||||
case GL_CULL_FACE: {
|
||||
GPUState.cull_face = GL_TRUE;
|
||||
GL_CONTEXT.gen.culling = _calc_pvr_face_culling();
|
||||
} break;
|
||||
case GL_DEPTH_TEST: {
|
||||
GPUState.depth_test_enabled = GL_TRUE;
|
||||
GL_CONTEXT.depth.comparison = _calc_pvr_depth_test();
|
||||
} break;
|
||||
case GL_BLEND: {
|
||||
GPUState.blend_enabled = GL_TRUE;
|
||||
_updatePVRBlend(&GL_CONTEXT);
|
||||
} break;
|
||||
case GL_SCISSOR_TEST: {
|
||||
GL_CONTEXT.gen.clip_mode = GPU_USERCLIP_INSIDE;
|
||||
_glApplyScissor(false);
|
||||
GPUState.scissor_test_enabled = GL_TRUE;
|
||||
} break;
|
||||
case GL_LIGHTING: {
|
||||
GPUState.lighting_enabled = GL_TRUE;
|
||||
} break;
|
||||
case GL_FOG:
|
||||
GL_CONTEXT.gen.fog_type = GPU_FOG_TABLE;
|
||||
GPUState.fog_enabled = GL_TRUE;
|
||||
break;
|
||||
case GL_COLOR_MATERIAL:
|
||||
GPUState.color_material_enabled = GL_TRUE;
|
||||
|
@ -455,7 +424,6 @@ GLAPI void APIENTRY glEnable(GLenum cap) {
|
|||
break;
|
||||
case GL_ALPHA_TEST: {
|
||||
GPUState.alpha_test_enabled = GL_TRUE;
|
||||
_updatePVRBlend(&GL_CONTEXT);
|
||||
} break;
|
||||
case GL_LIGHT0:
|
||||
case GL_LIGHT1:
|
||||
|
@ -495,24 +463,21 @@ GLAPI void APIENTRY glDisable(GLenum cap) {
|
|||
} break;
|
||||
case GL_CULL_FACE: {
|
||||
GPUState.culling_enabled = GL_FALSE;
|
||||
GL_CONTEXT.gen.culling = _calc_pvr_face_culling();
|
||||
} break;
|
||||
case GL_DEPTH_TEST: {
|
||||
GPUState.depth_test_enabled = GL_FALSE;
|
||||
GL_CONTEXT.depth.comparison = _calc_pvr_depth_test();
|
||||
} break;
|
||||
case GL_BLEND:
|
||||
GPUState.blend_enabled = GL_FALSE;
|
||||
_updatePVRBlend(&GL_CONTEXT);
|
||||
break;
|
||||
case GL_SCISSOR_TEST: {
|
||||
GL_CONTEXT.gen.clip_mode = GPU_USERCLIP_DISABLE;
|
||||
GPUState.scissor_test_enabled = GL_FALSE;
|
||||
} break;
|
||||
case GL_LIGHTING: {
|
||||
GPUState.lighting_enabled = GL_FALSE;
|
||||
} break;
|
||||
case GL_FOG:
|
||||
GL_CONTEXT.gen.fog_type = GPU_FOG_DISABLE;
|
||||
GPUState.fog_enabled = GL_FALSE;
|
||||
break;
|
||||
case GL_COLOR_MATERIAL:
|
||||
GPUState.color_material_enabled = GL_FALSE;
|
||||
|
@ -593,13 +558,13 @@ GLAPI void APIENTRY glReadBuffer(GLenum mode) {
|
|||
}
|
||||
|
||||
GLAPI void APIENTRY glDepthMask(GLboolean flag) {
|
||||
GL_CONTEXT.depth.write = (flag == GL_TRUE) ? GPU_DEPTHWRITE_ENABLE : GPU_DEPTHWRITE_DISABLE;
|
||||
GPUState.depth_mask_enabled = flag;
|
||||
GPUState.is_dirty = GL_TRUE;
|
||||
}
|
||||
|
||||
GLAPI void APIENTRY glDepthFunc(GLenum func) {
|
||||
GPUState.depth_func = func;
|
||||
GPUState.is_dirty = GL_TRUE;
|
||||
GL_CONTEXT.depth.comparison = _calc_pvr_depth_test();
|
||||
}
|
||||
|
||||
/* Hints */
|
||||
|
@ -621,22 +586,17 @@ GLAPI void APIENTRY glPolygonMode(GLenum face, GLenum mode) {
|
|||
GLAPI void APIENTRY glFrontFace(GLenum mode) {
|
||||
GPUState.front_face = mode;
|
||||
GPUState.is_dirty = GL_TRUE;
|
||||
GL_CONTEXT.gen.culling = _calc_pvr_face_culling();
|
||||
}
|
||||
|
||||
GLAPI void APIENTRY glCullFace(GLenum mode) {
|
||||
GPUState.cull_face = mode;
|
||||
GPUState.is_dirty = GL_TRUE;
|
||||
GL_CONTEXT.gen.culling = _calc_pvr_face_culling();
|
||||
}
|
||||
|
||||
GLenum _glGetShadeModel() {
|
||||
return (GL_CONTEXT.gen.shading == GPU_SHADE_FLAT) ? GL_FLAT : GL_SMOOTH;
|
||||
}
|
||||
|
||||
/* Shading - Flat or Goraud */
|
||||
GLAPI void APIENTRY glShadeModel(GLenum mode) {
|
||||
GL_CONTEXT.gen.shading = (mode == GL_SMOOTH) ? GPU_SHADE_GOURAUD : GPU_SHADE_FLAT;
|
||||
GPUState.shade_model = mode;
|
||||
GPUState.is_dirty = GL_TRUE;
|
||||
}
|
||||
|
||||
/* Blending */
|
||||
|
@ -644,7 +604,6 @@ GLAPI void APIENTRY glBlendFunc(GLenum sfactor, GLenum dfactor) {
|
|||
GPUState.blend_sfactor = sfactor;
|
||||
GPUState.blend_dfactor = dfactor;
|
||||
GPUState.is_dirty = GL_TRUE;
|
||||
_updatePVRBlend(&GL_CONTEXT);
|
||||
}
|
||||
|
||||
|
||||
|
@ -741,7 +700,7 @@ void APIENTRY glScissor(GLint x, GLint y, GLsizei width, GLsizei height) {
|
|||
*/
|
||||
void _glApplyScissor(bool force) {
|
||||
/* Don't do anyting if clipping is disabled */
|
||||
if(GL_CONTEXT.gen.clip_mode == GPU_USERCLIP_DISABLE) {
|
||||
if(!GPUState.scissor_test_enabled) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -800,7 +759,7 @@ GLboolean APIENTRY glIsEnabled(GLenum cap) {
|
|||
case GL_DEPTH_TEST:
|
||||
return GPUState.depth_test_enabled;
|
||||
case GL_SCISSOR_TEST:
|
||||
return GL_CONTEXT.gen.clip_mode == GPU_USERCLIP_INSIDE;
|
||||
return GPUState.scissor_test_enabled;
|
||||
case GL_CULL_FACE:
|
||||
return GPUState.culling_enabled;
|
||||
case GL_LIGHTING:
|
||||
|
|
Loading…
Reference in New Issue
Block a user