This commit is contained in:
Nishi 2026-02-03 10:41:50 +09:00
commit ee178645bf
Signed by: nishi
GPG key ID: 27EF69B208EB9343
4 changed files with 139 additions and 12 deletions

View file

@ -70,10 +70,12 @@ GSDECL void GSGLClearDepth(GSGL gl);
GSDECL void GSGLInitialTranslation(GSGL gl);
/* gl_camera.c */
GSDECL void GSGLCameraPerspective(GSGL gl, GSNumber width, GSNumber height);
GSDECL void GSGLCameraSet(GSGL gl);
GSDECL void GSGLCameraLookAt(GSGL gl, GSVector3 camera, GSVector3 look_at);
GSDECL void GSGLCameraSetup(GSGL gl);
GSDECL void GSGLCameraPerspective(GSGL gl, GSNumber width, GSNumber height);
GSDECL void GSGLCameraSet(GSGL gl);
GSDECL void GSGLCameraLookAt(GSGL gl, GSVector3 camera, GSVector3 look_at);
GSDECL void GSGLCameraSetup(GSGL gl);
GSDECL void GSGLCameraFrustum(GSGL gl);
GSDECL GSBool GSGLCameraFrustumContain(GSGL gl, GSVector3 a, GSVector3 b);
#ifdef __cplusplus
}

View file

@ -206,6 +206,11 @@ struct _GSGL {
GLdouble shadow_old_projection[16];
GLdouble shadow_old_modelview[16];
GLdouble frustum_projection[16];
GLdouble frustum_modelview[16];
GSNumber frustum_planes[6][16];
GSNumber frustum_clip[16];
GSBool bold;
};
@ -253,6 +258,8 @@ struct _GSModel {
float* vertex;
float* texcoord;
GSModelFace* face;
GSVector3 bbox[2];
};
struct _GSSound {

View file

@ -79,4 +79,93 @@ void GSGLCameraSetup(GSGL gl) {
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
GSGLCameraSet(gl);
GSGLCameraFrustum(gl);
}
static void frustum_normalize(GSGL gl, int plane) {
GSVector3 v;
GSNumber l;
int i;
v[0] = gl->frustum_planes[plane][0];
v[1] = gl->frustum_planes[plane][1];
v[2] = gl->frustum_planes[plane][2];
l = GSMathLength3(v);
for(i = 0; i < 4; i++) {
gl->frustum_planes[plane][i] /= l;
}
}
void GSGLCameraFrustum(GSGL gl) {
glGetDoublev(GL_PROJECTION_MATRIX, gl->frustum_projection);
glGetDoublev(GL_MODELVIEW_MATRIX, gl->frustum_modelview);
gl->frustum_clip[0x0] = gl->frustum_modelview[0x0] * gl->frustum_projection[0x0] + gl->frustum_modelview[0x1] * gl->frustum_projection[0x4] + gl->frustum_modelview[0x2] * gl->frustum_projection[0x8] + gl->frustum_modelview[0x3] * gl->frustum_projection[0xc];
gl->frustum_clip[0x1] = gl->frustum_modelview[0x0] * gl->frustum_projection[0x1] + gl->frustum_modelview[0x1] * gl->frustum_projection[0x5] + gl->frustum_modelview[0x2] * gl->frustum_projection[0x9] + gl->frustum_modelview[0x3] * gl->frustum_projection[0xd];
gl->frustum_clip[0x2] = gl->frustum_modelview[0x0] * gl->frustum_projection[0x2] + gl->frustum_modelview[0x1] * gl->frustum_projection[0x6] + gl->frustum_modelview[0x2] * gl->frustum_projection[0xa] + gl->frustum_modelview[0x3] * gl->frustum_projection[0xe];
gl->frustum_clip[0x3] = gl->frustum_modelview[0x0] * gl->frustum_projection[0x3] + gl->frustum_modelview[0x1] * gl->frustum_projection[0x7] + gl->frustum_modelview[0x2] * gl->frustum_projection[0xb] + gl->frustum_modelview[0x3] * gl->frustum_projection[0xf];
gl->frustum_clip[0x4] = gl->frustum_modelview[0x4] * gl->frustum_projection[0x0] + gl->frustum_modelview[0x5] * gl->frustum_projection[0x4] + gl->frustum_modelview[0x6] * gl->frustum_projection[0x8] + gl->frustum_modelview[0x7] * gl->frustum_projection[0xc];
gl->frustum_clip[0x5] = gl->frustum_modelview[0x4] * gl->frustum_projection[0x1] + gl->frustum_modelview[0x5] * gl->frustum_projection[0x5] + gl->frustum_modelview[0x6] * gl->frustum_projection[0x9] + gl->frustum_modelview[0x7] * gl->frustum_projection[0xd];
gl->frustum_clip[0x6] = gl->frustum_modelview[0x4] * gl->frustum_projection[0x2] + gl->frustum_modelview[0x5] * gl->frustum_projection[0x6] + gl->frustum_modelview[0x6] * gl->frustum_projection[0xa] + gl->frustum_modelview[0x7] * gl->frustum_projection[0xe];
gl->frustum_clip[0x7] = gl->frustum_modelview[0x4] * gl->frustum_projection[0x3] + gl->frustum_modelview[0x5] * gl->frustum_projection[0x7] + gl->frustum_modelview[0x6] * gl->frustum_projection[0xb] + gl->frustum_modelview[0x7] * gl->frustum_projection[0xf];
gl->frustum_clip[0x8] = gl->frustum_modelview[0x8] * gl->frustum_projection[0x0] + gl->frustum_modelview[0x9] * gl->frustum_projection[0x4] + gl->frustum_modelview[0xa] * gl->frustum_projection[0x8] + gl->frustum_modelview[0xb] * gl->frustum_projection[0xc];
gl->frustum_clip[0x9] = gl->frustum_modelview[0x8] * gl->frustum_projection[0x1] + gl->frustum_modelview[0x9] * gl->frustum_projection[0x5] + gl->frustum_modelview[0xa] * gl->frustum_projection[0x9] + gl->frustum_modelview[0xb] * gl->frustum_projection[0xd];
gl->frustum_clip[0xa] = gl->frustum_modelview[0x8] * gl->frustum_projection[0x2] + gl->frustum_modelview[0x9] * gl->frustum_projection[0x6] + gl->frustum_modelview[0xa] * gl->frustum_projection[0xa] + gl->frustum_modelview[0xb] * gl->frustum_projection[0xe];
gl->frustum_clip[0xb] = gl->frustum_modelview[0x8] * gl->frustum_projection[0x3] + gl->frustum_modelview[0x9] * gl->frustum_projection[0x7] + gl->frustum_modelview[0xa] * gl->frustum_projection[0xb] + gl->frustum_modelview[0xb] * gl->frustum_projection[0xf];
gl->frustum_clip[0xc] = gl->frustum_modelview[0xc] * gl->frustum_projection[0x0] + gl->frustum_modelview[0xd] * gl->frustum_projection[0x4] + gl->frustum_modelview[0xe] * gl->frustum_projection[0x8] + gl->frustum_modelview[0xf] * gl->frustum_projection[0xc];
gl->frustum_clip[0xd] = gl->frustum_modelview[0xc] * gl->frustum_projection[0x1] + gl->frustum_modelview[0xd] * gl->frustum_projection[0x5] + gl->frustum_modelview[0xe] * gl->frustum_projection[0x9] + gl->frustum_modelview[0xf] * gl->frustum_projection[0xd];
gl->frustum_clip[0xe] = gl->frustum_modelview[0xc] * gl->frustum_projection[0x2] + gl->frustum_modelview[0xd] * gl->frustum_projection[0x6] + gl->frustum_modelview[0xe] * gl->frustum_projection[0xa] + gl->frustum_modelview[0xf] * gl->frustum_projection[0xe];
gl->frustum_clip[0xf] = gl->frustum_modelview[0xc] * gl->frustum_projection[0x3] + gl->frustum_modelview[0xd] * gl->frustum_projection[0x7] + gl->frustum_modelview[0xe] * gl->frustum_projection[0xb] + gl->frustum_modelview[0xf] * gl->frustum_projection[0xf];
gl->frustum_planes[0][0] = gl->frustum_clip[0x3] - gl->frustum_clip[0x0];
gl->frustum_planes[0][1] = gl->frustum_clip[0x7] - gl->frustum_clip[0x4];
gl->frustum_planes[0][2] = gl->frustum_clip[0xb] - gl->frustum_clip[0x8];
gl->frustum_planes[0][3] = gl->frustum_clip[0xf] - gl->frustum_clip[0xc];
frustum_normalize(gl, 0);
gl->frustum_planes[1][0] = gl->frustum_clip[0x3] + gl->frustum_clip[0x0];
gl->frustum_planes[1][1] = gl->frustum_clip[0x7] + gl->frustum_clip[0x4];
gl->frustum_planes[1][2] = gl->frustum_clip[0xb] + gl->frustum_clip[0x8];
gl->frustum_planes[1][3] = gl->frustum_clip[0xf] + gl->frustum_clip[0xc];
frustum_normalize(gl, 1);
gl->frustum_planes[2][0] = gl->frustum_clip[0x3] - gl->frustum_clip[0x1];
gl->frustum_planes[2][1] = gl->frustum_clip[0x7] - gl->frustum_clip[0x5];
gl->frustum_planes[2][2] = gl->frustum_clip[0xb] - gl->frustum_clip[0x9];
gl->frustum_planes[2][3] = gl->frustum_clip[0xf] - gl->frustum_clip[0xd];
frustum_normalize(gl, 2);
gl->frustum_planes[3][0] = gl->frustum_clip[0x3] + gl->frustum_clip[0x1];
gl->frustum_planes[3][1] = gl->frustum_clip[0x7] + gl->frustum_clip[0x5];
gl->frustum_planes[3][2] = gl->frustum_clip[0xb] + gl->frustum_clip[0x9];
gl->frustum_planes[3][3] = gl->frustum_clip[0xf] + gl->frustum_clip[0xd];
frustum_normalize(gl, 3);
gl->frustum_planes[4][0] = gl->frustum_clip[0x3] - gl->frustum_clip[0x2];
gl->frustum_planes[4][1] = gl->frustum_clip[0x7] - gl->frustum_clip[0x6];
gl->frustum_planes[4][2] = gl->frustum_clip[0xb] - gl->frustum_clip[0xa];
gl->frustum_planes[4][3] = gl->frustum_clip[0xf] - gl->frustum_clip[0xe];
frustum_normalize(gl, 4);
gl->frustum_planes[5][0] = gl->frustum_clip[0x3] + gl->frustum_clip[0x2];
gl->frustum_planes[5][1] = gl->frustum_clip[0x7] + gl->frustum_clip[0x6];
gl->frustum_planes[5][2] = gl->frustum_clip[0xb] + gl->frustum_clip[0xa];
gl->frustum_planes[5][3] = gl->frustum_clip[0xf] + gl->frustum_clip[0xe];
frustum_normalize(gl, 5);
}
GSBool GSGLCameraFrustumContain(GSGL gl, GSVector3 a, GSVector3 b) {
int i;
for(i = 0; i < 6; i++) {
GSBool bv = GSTrue;
bv = bv && gl->frustum_planes[i][0] * a[0] + gl->frustum_planes[i][1] * a[1] + gl->frustum_planes[i][2] * a[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * b[0] + gl->frustum_planes[i][1] * a[1] + gl->frustum_planes[i][2] * a[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * a[0] + gl->frustum_planes[i][1] * b[1] + gl->frustum_planes[i][2] * a[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * b[0] + gl->frustum_planes[i][1] * b[1] + gl->frustum_planes[i][2] * a[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * a[0] + gl->frustum_planes[i][1] * a[1] + gl->frustum_planes[i][2] * b[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * b[0] + gl->frustum_planes[i][1] * a[1] + gl->frustum_planes[i][2] * b[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * a[0] + gl->frustum_planes[i][1] * b[1] + gl->frustum_planes[i][2] * b[2] + gl->frustum_planes[i][3] <= 0.0;
bv = bv && gl->frustum_planes[i][0] * b[0] + gl->frustum_planes[i][1] * b[1] + gl->frustum_planes[i][2] * b[2] + gl->frustum_planes[i][3] <= 0.0;
if(bv) return GSFalse;
}
return GSTrue;
}

View file

@ -10,13 +10,17 @@
#include <stb_ds.h>
static void parse_obj(GSModel model, char* txt) {
char* f = txt;
float lm = 0; /* leftmost */
float rm = 0; /* rightmost */
float um = 0; /* upmost */
float dm = 0; /* downmost */
float fm = 0; /* frontmost */
float bm = 0; /* backmost */
char* f = txt;
float lm = 0; /* leftmost */
float rm = 0; /* rightmost */
float um = 0; /* upmost */
float dm = 0; /* downmost */
float fm = 0; /* frontmost */
float bm = 0; /* backmost */
float l = 0;
float blr = fabs(lm - rm);
float bud = fabs(um - dm);
float bbf = fabs(fm - bm);
while(1) {
char* s = strchr(f, '\n');
@ -158,6 +162,22 @@ static void parse_obj(GSModel model, char* txt) {
if(s == NULL) break;
f = s + 1;
}
blr = fabs(lm - rm);
bud = fabs(um - dm);
bbf = fabs(fm - bm);
if(l < blr) l = blr;
if(l < bud) l = bud;
if(l < bbf) l = bbf;
model->bbox[0][0] = l;
model->bbox[0][1] = l;
model->bbox[0][2] = l;
model->bbox[1][0] = -model->bbox[0][0];
model->bbox[1][1] = -model->bbox[0][1];
model->bbox[1][2] = -model->bbox[0][2];
}
static void parse_mtl(GSModel model, char* txt) {
@ -316,7 +336,16 @@ void GSModelDraw(GSModel model, GSVector3 pos, GSRotation* rot) {
GSGLTextureSet(gl, 0);
} else {
GSGLCallList(gl, model->call_list);
GSVector3 a, b;
for(i = 0; i < 3; i++) {
a[i] = b[i] = pos[i];
a[i] += model->bbox[0][i];
b[i] += model->bbox[1][i];
}
if(GSGLCameraFrustumContain(gl, a, b)) GSGLCallList(gl, model->call_list);
}
GSGLPopMatrix(gl);
}