Stub out lighting functionality

This commit is contained in:
Luke Benstead 2018-05-12 14:05:54 +01:00
parent 62e001c288
commit e96d379796
7 changed files with 239 additions and 179 deletions

View File

@ -162,6 +162,8 @@ static void submitVertices(GLenum mode, GLsizei first, GLsizei count, GLenum typ
const GLubyte* indices_as_bytes = (GLubyte*) indices;
GLboolean lighting_enabled = isLightingEnabled();
for(GLuint i = first; i < count; ++i) {
pvr_vertex_t* vertex = (pvr_vertex_t*) dst;
vertex->u = vertex->v = 0.0f;
@ -193,6 +195,20 @@ static void submitVertices(GLenum mode, GLsizei first, GLsizei count, GLenum typ
_parseFloats(normal, nptr + (idx * nstride), NORMAL_POINTER.size, NORMAL_POINTER.type);
}
if(lighting_enabled) {
GLfloat contribution[4];
uint32 to_add;
for(GLubyte i = 0; i < MAX_LIGHTS; ++i) {
if(isLightEnabled(i)) {
calculateLightingContribution(i, &vertex->x, normal, contribution);
to_add = PVR_PACK_COLOR(contribution[0], contribution[1], contribution[2], contribution[3]);
/* FIXME: Add the colour to argb */
}
}
}
++dst;
}
}

View File

@ -66,6 +66,7 @@ void APIENTRY glKosInit() {
initAttributePointers();
initContext();
initLights();
_glKosInitMatrix();
_glKosInitTextures();

View File

@ -0,0 +1,139 @@
#include "private.h"
static GLfloat SCENE_AMBIENT [] = {0.2, 0.2, 0.2, 1.0};
static GLboolean VIEWER_IN_EYE_COORDINATES = GL_TRUE;
static GLenum COLOR_CONTROL = GL_SINGLE_COLOR;
static GLboolean TWO_SIDED_LIGHTING = GL_FALSE;
static LightSource LIGHTS[MAX_LIGHTS];
static Material MATERIAL;
void initLights() {
static GLfloat ONE [] = {1.0f, 1.0f, 1.0f, 1.0f};
static GLfloat ZERO [] = {0.0f, 0.0f, 0.0f, 1.0f};
static GLfloat PARTIAL [] = {0.2f, 0.2f, 0.2f, 1.0f};
static GLfloat MOSTLY [] = {0.8f, 0.8f, 0.8f, 1.0f};
memcpy(MATERIAL.ambient, PARTIAL, sizeof(GLfloat) * 4);
memcpy(MATERIAL.diffuse, MOSTLY, sizeof(GLfloat) * 4);
memcpy(MATERIAL.specular, ZERO, sizeof(GLfloat) * 4);
memcpy(MATERIAL.emissive, ZERO, sizeof(GLfloat) * 4);
MATERIAL.exponent = 0.0f;
MATERIAL.ambient_color_index = 0.0f;
MATERIAL.diffuse_color_index = 1.0f;
MATERIAL.specular_color_index = 1.0f;
for(GLubyte i = 0; i < MAX_LIGHTS; ++i) {
memcpy(LIGHTS[i].ambient, ZERO, sizeof(GLfloat) * 4);
memcpy(LIGHTS[i].diffuse, ONE, sizeof(GLfloat) * 4);
memcpy(LIGHTS[i].specular, ONE, sizeof(GLfloat) * 4);
if(i > 0) {
memcpy(LIGHTS[i].diffuse, ZERO, sizeof(GLfloat) * 4);
memcpy(LIGHTS[i].specular, ZERO, sizeof(GLfloat) * 4);
}
LIGHTS[i].position[0] = LIGHTS[i].position[1] = LIGHTS[i].position[3] = 0.0f;
LIGHTS[i].position[2] = 1.0f;
LIGHTS[i].spot_direction[0] = LIGHTS[i].spot_direction[1] = 0.0f;
LIGHTS[i].spot_direction[2] = -1.0f;
LIGHTS[i].spot_exponent = 0.0f;
LIGHTS[i].spot_cutoff = 180.0f;
LIGHTS[i].constant_attenuation = 1.0f;
LIGHTS[i].linear_attenuation = 0.0f;
LIGHTS[i].quadratic_attenuation = 0.0f;
}
}
void APIENTRY glLightModelf(GLenum pname, const GLfloat param) {
glLightModelfv(pname, &param);
}
void APIENTRY glLightModeli(GLenum pname, const GLint param) {
glLightModeliv(pname, &param);
}
void APIENTRY glLightModelfv(GLenum pname, const GLfloat *params) {
switch(pname) {
case GL_LIGHT_MODEL_AMBIENT:
memcpy(SCENE_AMBIENT, params, sizeof(GLfloat) * 4);
break;
case GL_LIGHT_MODEL_LOCAL_VIEWER:
VIEWER_IN_EYE_COORDINATES = (*params) ? GL_TRUE : GL_FALSE;
break;
case GL_LIGHT_MODEL_TWO_SIDE:
/* Not implemented */
default:
_glKosThrowError(GL_INVALID_ENUM, __func__);
_glKosPrintError();
}
}
void APIENTRY glLightModeliv(GLenum pname, const GLint* params) {
switch(pname) {
case GL_LIGHT_MODEL_COLOR_CONTROL:
COLOR_CONTROL = *params;
break;
case GL_LIGHT_MODEL_LOCAL_VIEWER:
VIEWER_IN_EYE_COORDINATES = (*params) ? GL_TRUE : GL_FALSE;
break;
default:
_glKosThrowError(GL_INVALID_ENUM, __func__);
_glKosPrintError();
}
}
void APIENTRY glLightfv(GLenum light, GLenum pname, const GLfloat *params) {
GLubyte idx = light & 0xF;
if(idx >= MAX_LIGHTS) {
return;
}
switch(pname) {
case GL_AMBIENT:
memcpy(LIGHTS[idx].ambient, params, sizeof(GLfloat) * 4);
break;
case GL_DIFFUSE:
memcpy(LIGHTS[idx].diffuse, params, sizeof(GLfloat) * 4);
break;
case GL_SPECULAR:
memcpy(LIGHTS[idx].specular, params, sizeof(GLfloat) * 4);
break;
case GL_POSITION:
memcpy(LIGHTS[idx].position, params, sizeof(GLfloat) * 4);
break;
case GL_SPOT_CUTOFF:
case GL_SPOT_DIRECTION:
case GL_SPOT_EXPONENT:
case GL_CONSTANT_ATTENUATION:
case GL_LINEAR_ATTENUATION:
case GL_QUADRATIC_ATTENUATION:
default:
_glKosThrowError(GL_INVALID_ENUM, __func__);
_glKosPrintError();
}
}
void APIENTRY glLightf(GLenum light, GLenum pname, GLfloat param) {
}
void APIENTRY glMateriali(GLenum face, GLenum pname, const GLint param) {
}
void APIENTRY glMaterialf(GLenum face, GLenum pname, const GLfloat param) {
}
void APIENTRY glMaterialfv(GLenum face, GLenum pname, const GLfloat *params) {
}
void calculateLightingContribution(const GLint light, const GLfloat* pos, const GLfloat* normal, GLfloat* colour) {
}

View File

@ -41,10 +41,37 @@ typedef struct {
GLvoid *data;
} TextureObject;
typedef struct {
GLfloat ambient[4];
GLfloat diffuse[4];
GLfloat specular[4];
GLfloat emissive[4];
GLfloat exponent;
GLfloat ambient_color_index;
GLfloat diffuse_color_index;
GLfloat specular_color_index;
} Material;
typedef struct {
GLfloat ambient[4];
GLfloat diffuse[4];
GLfloat specular[4];
GLfloat position[4];
GLfloat spot_direction[3];
GLfloat spot_exponent;
GLfloat spot_cutoff;
GLfloat constant_attenuation;
GLfloat linear_attenuation;
GLfloat quadratic_attenuation;
} LightSource;
PolyList *activePolyList();
void initAttributePointers();
void initContext();
void initLights();
pvr_poly_cxt_t* getPVRContext();
GLubyte _glKosInitTextures();
void updatePVRTextureContext(pvr_poly_cxt_t* context, TextureObject* tx1);
@ -53,8 +80,13 @@ TextureObject* getTexture1();
TextureObject* getBoundTexture();
GLboolean isBlendingEnabled();
GLboolean isLightingEnabled();
GLboolean isLightEnabled(GLubyte light);
void calculateLightingContribution(const GLint light, const GLfloat* pos, const GLfloat* normal, GLfloat* colour);
#define PVR_VERTEX_BUF_SIZE 2560 * 256
#define MAX_TEXTURE_UNITS 2
#define MAX_LIGHTS 8
#define CLAMP( X, MIN, MAX ) ( (X)<(MIN) ? (MIN) : ((X)>(MAX) ? (MAX) : (X)) )

View File

@ -150,6 +150,16 @@ void updatePVRTextureContext(pvr_poly_cxt_t* context, TextureObject *tx1) {
}
}
static GLboolean LIGHTING_ENABLED = GL_FALSE;
static GLboolean LIGHT_ENABLED[MAX_LIGHTS];
GLboolean isLightingEnabled() {
return LIGHTING_ENABLED;
}
GLboolean isLightEnabled(unsigned char light) {
return LIGHT_ENABLED[light & 0xF];
}
static GLfloat CLEAR_COLOUR[3];
@ -176,6 +186,11 @@ void initContext() {
glDisable(GL_BLEND);
glDisable(GL_DEPTH_TEST);
glDisable(GL_TEXTURE_2D);
glDisable(GL_LIGHTING);
for(GLubyte i = 0; i < MAX_LIGHTS; ++i) {
glDisable(GL_LIGHT0 + i);
}
}
GLAPI void APIENTRY glEnable(GLenum cap) {
@ -198,6 +213,19 @@ GLAPI void APIENTRY glEnable(GLenum cap) {
case GL_SCISSOR_TEST: {
GL_CONTEXT.gen.clip_mode = PVR_USERCLIP_INSIDE;
} break;
case GL_LIGHTING: {
LIGHTING_ENABLED = GL_TRUE;
} break;
case GL_LIGHT0:
case GL_LIGHT1:
case GL_LIGHT2:
case GL_LIGHT3:
case GL_LIGHT4:
case GL_LIGHT5:
case GL_LIGHT6:
case GL_LIGHT7:
LIGHT_ENABLED[cap & 0xF] = GL_TRUE;
break;
default:
break;
}
@ -223,6 +251,19 @@ GLAPI void APIENTRY glDisable(GLenum cap) {
case GL_SCISSOR_TEST: {
GL_CONTEXT.gen.clip_mode = PVR_USERCLIP_DISABLE;
} break;
case GL_LIGHTING: {
LIGHTING_ENABLED = GL_FALSE;
} break;
case GL_LIGHT0:
case GL_LIGHT1:
case GL_LIGHT2:
case GL_LIGHT3:
case GL_LIGHT4:
case GL_LIGHT5:
case GL_LIGHT6:
case GL_LIGHT7:
LIGHT_ENABLED[cap & 0xF] = GL_FALSE;
break;
default:
break;
}

View File

@ -107,18 +107,6 @@ void glNormal3fv(const GLfloat *xyz) {
GL_VERTEX_NORMAL[2] = xyz[2];
}
void glLightModelfv(GLenum pname, const GLfloat *params) {
if(pname != GL_LIGHT_MODEL_AMBIENT) {
_glKosThrowError(GL_INVALID_ENUM, "glLightModelfv");
return;
}
GL_GLOBAL_AMBIENT[0] = params[0];
GL_GLOBAL_AMBIENT[1] = params[1];
GL_GLOBAL_AMBIENT[2] = params[2];
GL_GLOBAL_AMBIENT[3] = params[3];
}
/* Misc Lighting Functions ************************************/
static inline void glCopyRGBA(const rgba *src, rgba *dst) {
*dst = *src;
@ -132,173 +120,6 @@ static inline void glCopy3f(const float *src, float *dst) {
memcpy(dst, src, 0xC);
}
/* GL Light Parameters ******************************************************/
void glLightfv(GLenum light, GLenum pname, const GLfloat *params) {
if(light < GL_LIGHT0 || light > GL_LIGHT0 + GL_KOS_MAX_LIGHTS) return;
switch(pname) {
case GL_AMBIENT:
glCopyRGBA((rgba *)params, (rgba *)&GL_LIGHTS[light & 0xF].Ka);
break;
case GL_DIFFUSE:
glCopyRGBA((rgba *)params, (rgba *)&GL_LIGHTS[light & 0xF].Kd);
break;
case GL_SPECULAR:
glCopyRGBA((rgba *)params, (rgba *)&GL_LIGHTS[light & 0xF].Ks);
break;
case GL_POSITION:
glCopy4f(params, &GL_LIGHTS[light & 0xF].Pos[0]);
break;
case GL_SPOT_DIRECTION:
glCopy3f(params, &GL_LIGHTS[light & 0xF].Dir[0]);
break;
case GL_SPOT_EXPONENT:
GL_LIGHTS[light & 0xF].Exponent = *params;
break;
case GL_SPOT_CUTOFF:
if(*params >= 0.0f && *params <= 180.0f)
GL_LIGHTS[light & 0xF].CutOff = LCOS(*params);
break;
case GL_CONSTANT_ATTENUATION:
if(*params >= 0)
GL_LIGHTS[light & 0xF].Kc = *params;
else
GL_LIGHTS[light & 0xF].Kc = 0;
break;
case GL_LINEAR_ATTENUATION:
if(*params >= 0)
GL_LIGHTS[light & 0xF].Kl = *params;
else
GL_LIGHTS[light & 0xF].Kl = 0;
break;
case GL_QUADRATIC_ATTENUATION:
if(*params >= 0)
GL_LIGHTS[light & 0xF].Kq = *params;
else
GL_LIGHTS[light & 0xF].Kq = 0;
break;
case GL_AMBIENT_AND_DIFFUSE:
glCopyRGBA((rgba *)params, (rgba *)&GL_LIGHTS[light & 0xF].Ka);
glCopyRGBA((rgba *)params, (rgba *)&GL_LIGHTS[light & 0xF].Kd);
break;
}
}
void glLightf(GLenum light, GLenum pname, GLfloat param) {
if(light < GL_LIGHT0 || light > GL_LIGHT0 + GL_KOS_MAX_LIGHTS) return;
switch(pname) {
case GL_CONSTANT_ATTENUATION:
if(param >= 0)
GL_LIGHTS[light & 0xF].Kc = param;
else
GL_LIGHTS[light & 0xF].Kc = 0;
break;
case GL_LINEAR_ATTENUATION:
if(param >= 0)
GL_LIGHTS[light & 0xF].Kl = param;
else
GL_LIGHTS[light & 0xF].Kl = 0;
break;
case GL_QUADRATIC_ATTENUATION:
if(param >= 0)
GL_LIGHTS[light & 0xF].Kq = param;
else
GL_LIGHTS[light & 0xF].Kq = 0;
break;
case GL_SPOT_CUTOFF:
if(param >= 0.0f && param <= 180.0f)
GL_LIGHTS[light & 0xF].CutOff = LCOS(param);
break;
case GL_SPOT_EXPONENT:
GL_LIGHTS[light & 0xF].Exponent = param;
break;
}
}
/* GL Material Parameters **************************************************/
void glMateriali(GLenum face, GLenum pname, const GLint param) {
//if(face!=GL_FRONT_AND_BACK) return;
if(pname == GL_SHININESS) {
if(param < 0)
GL_MATERIAL.Shine = 0;
else if(param > 128)
GL_MATERIAL.Shine = 128;
else
GL_MATERIAL.Shine = param;
}
}
void glMaterialf(GLenum face, GLenum pname, const GLfloat param) {
//if(face!=GL_FRONT_AND_BACK) return;
if(pname == GL_SHININESS) {
if(param < 0)
GL_MATERIAL.Shine = 0;
else if(param > 128.0)
GL_MATERIAL.Shine = 128.0;
else
GL_MATERIAL.Shine = param;
}
}
void glMaterialfv(GLenum face, GLenum pname, const GLfloat *params) {
//if(face!=GL_FRONT_AND_BACK) return;
switch(pname) {
case GL_AMBIENT:
glCopyRGBA((rgba *)params, (rgba *)&GL_MATERIAL.Ka[0]);
break;
case GL_DIFFUSE:
glCopyRGBA((rgba *)params, (rgba *)&GL_MATERIAL.Kd[0]);
break;
case GL_SPECULAR:
glCopyRGBA((rgba *)params, (rgba *)&GL_MATERIAL.Ks[0]);
break;
case GL_EMISSION:
glCopyRGBA((rgba *)params, (rgba *)&GL_MATERIAL.Ke[0]);
break;
case GL_SHININESS:
glMaterialf(GL_FRONT_AND_BACK, pname, *params);
break;
case GL_AMBIENT_AND_DIFFUSE:
glCopyRGBA((rgba *)params, (rgba *)&GL_MATERIAL.Ka[0]);
glCopyRGBA((rgba *)params, (rgba *)&GL_MATERIAL.Kd[0]);
break;
}
}
/* Vertex Lighting **********************************************************/
/* Fast POW Implementation - Less accurate, but much faster than math.h */

View File

@ -235,6 +235,11 @@ __BEGIN_DECLS
#define GL_LIGHT14 0x400E
#define GL_LIGHT15 0x400F
/* EXT_separate_specular_color.txt */
#define GL_LIGHT_MODEL_COLOR_CONTROL 0x81F8
#define GL_SINGLE_COLOR 0x81F9
#define GL_SEPARATE_SPECULAR_COLOR 0x81FA
/* Client state caps */
#define GL_VERTEX_ARRAY 0x8074
#define GL_NORMAL_ARRAY 0x8075
@ -620,7 +625,12 @@ GLAPI void APIENTRY glFogfv(GLenum pname, const GLfloat *params);
/* Set Individual Light Parameters */
GLAPI void APIENTRY glLightfv(GLenum light, GLenum pname, const GLfloat *params);
GLAPI void APIENTRY glLightf(GLenum light, GLenum pname, GLfloat param);
GLAPI void APIENTRY glLightModelf(GLenum pname, const GLfloat param);
GLAPI void APIENTRY glLightModeli(GLenum pname, const GLint param);
GLAPI void APIENTRY glLightModelfv(GLenum pname, const GLfloat *params);
GLAPI void APIENTRY glLightModeliv(GLenum pname, const GLint *params);
/* Set Global Material Parameters */
GLAPI void APIENTRY glMateriali(GLenum face, GLenum pname, const GLint param);