shithub: 3dee

Download patch

ref: 3a84c951f3921fc3204538fb9ffed9242f23aae7
parent: 0a6263083c9a63afcbcbc5862a6be940f13b62be
author: rodri <rgl@antares-labs.eu>
date: Fri Apr 4 18:22:18 EDT 2025

vis: adjust camera poses based on the scene

--- a/vis.c
+++ b/vis.c
@@ -12,11 +12,24 @@
 
 #define isdigit(c) ((c) >= '0' && (c) <= '9')
 
+typedef struct AABB AABB;
+struct AABB
+{
+	Point3 min;
+	Point3 max;
+	/* with its homologous bounding sphere */
+	Point3 c;
+	double r;
+};
+
 typedef struct Camcfg Camcfg;
 struct Camcfg
 {
-	Point3 p, lookat, up;
-	double fov, clipn, clipf;
+	Point3 p;
+	Point3 lookat;
+	Point3 up;
+	double fov;
+	double clipn, clipf;
 	int ptype;
 };
 
@@ -61,6 +74,7 @@
 Scene *scene;
 Mouse om;
 Quaternion orient = {1,0,0,0};
+AABB scenebbox;
 
 Camera *cams[4], *maincam;
 Camcfg camcfgs[4] = {
@@ -126,6 +140,30 @@
 }
 
 void
+updatebbox(Entity *e)
+{
+	static int inited;
+	Model *m;
+	Primitive *prim;
+	Vertex *v;
+
+	m = e->mdl;
+	for(prim = m->prims; prim < m->prims + m->nprims; prim++)
+	for(v = prim->v; v < prim->v + prim->type+1; v++){
+		if(!inited){
+			scenebbox.min = scenebbox.max = addpt3(e->p, v->p);
+			inited++;
+			continue;
+		}
+
+		scenebbox.min = minpt3(scenebbox.min, addpt3(e->p, v->p));
+		scenebbox.max = maxpt3(scenebbox.max, addpt3(e->p, v->p));
+	}
+	scenebbox.c = divpt3(addpt3(scenebbox.max, scenebbox.min), 2);
+	scenebbox.r = max(vec3len(scenebbox.min), vec3len(scenebbox.max));
+}
+
+void
 drawstats(void)
 {
 	int i, camno;
@@ -599,6 +637,7 @@
 		mdl->addprim(mdl, t[1]);
 		ent = newentity(nil, mdl);
 		scene->addent(scene, ent);
+		updatebbox(ent);
 	}
 }
 
@@ -650,7 +689,6 @@
 	Primitive *prim;
 	char *texpath, *mdlpath, *s;
 	int i, fd, fbw, fbh, scale;
-	int blendtest = 0;
 
 	GEOMfmtinstall();
 	texpath = nil;
@@ -674,8 +712,6 @@
 	case 'p': doprof++; break;
 	default: usage();
 	}ARGEND;
-	if(argc < 1)
-		blendtest++;
 
 	confproc();
 
@@ -683,7 +719,7 @@
 		sysfatal("couldn't find gouraud shader");
 
 	scene = newscene(nil);
-	if(blendtest)
+	if(argc < 1)
 		mkblendtestscene();
 	else
 	while(argc--){
@@ -698,7 +734,10 @@
 		subject = newentity(mdlpath, model);
 //		subject->p.z = -argc*4;
 		scene->addent(scene, subject);
+		updatebbox(subject);
 
+fprint(2, "%s: %lud prims\n", mdlpath, model->nprims);
+
 		if(argc == 0 && texpath != nil){
 			fd = open(texpath, OREAD);
 			if(fd < 0)
@@ -750,7 +789,8 @@
 				camcfgs[i].ptype, camcfgs[i].fov, camcfgs[i].clipn, camcfgs[i].clipf);
 		if(cams[i] == nil)
 			sysfatal("Camv: %r");
-		placecamera(cams[i], scene, camcfgs[i].p, camcfgs[i].lookat, camcfgs[i].up);
+		placecamera(cams[i], scene, addpt3(scenebbox.c, mulpt3(normvec3(camcfgs[i].p), 1.5*scenebbox.r)), scenebbox.c, camcfgs[i].up);
+		cams[i]->p.w = 1;
 	}
 	maincam = cams[3];
 	lights[0].p = Pt3(0,100,100,1);