ccdemos/common_sdl.h
branchpyrit
changeset 39 7079dcc3bd74
child 40 929aad02c5f2
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/ccdemos/common_sdl.h	Fri Dec 14 16:51:22 2007 +0100
@@ -0,0 +1,151 @@
+#include <SDL.h>
+
+Uint32 fp10s_acc = 0;
+Uint32 fp10s_acc_samples = 0;
+
+int w = 512;
+int h = 384;
+
+void update(Raytracer &rt, SDL_Surface *screen, Float *render_buffer)
+{
+	static Uint32 t = 0;
+	Uint32 tnow = SDL_GetTicks();
+	int fp10s = 10000/(int)(tnow - t);
+	if (t != 0)
+	{
+		fp10s_acc += fp10s;
+		++fp10s_acc_samples;
+	}
+	t = tnow;
+	printf("\b\b\b\b\b\b\b\b\bfps:%3d.%1d", fp10s/10, fp10s%10);
+	fflush(stdout);
+
+	rt.render(w, h, render_buffer);
+
+	if (SDL_MUSTLOCK(screen))
+		if (SDL_LockSurface(screen) < 0)
+			return;
+
+	Uint32 *bufp = (Uint32 *)screen->pixels;
+	unsigned char c[3];
+	for (Float *fd = render_buffer; fd != render_buffer + w*h*3; fd += 3)
+	{
+		for (int i = 0; i < 3; i++)
+		{
+			if (fd[i] > 1.0)
+				c[i] = 255;
+			else
+				c[i] = (unsigned char)(fd[i] * 255.0);
+		}
+		*bufp = SDL_MapRGB(screen->format, c[0], c[1], c[2]);
+		bufp++;
+	}
+
+	if (SDL_MUSTLOCK(screen))
+		SDL_UnlockSurface(screen);
+
+	if (screen->flags & SDL_DOUBLEBUF)
+		SDL_Flip(screen);
+	else
+		SDL_UpdateRect(screen, 0, 0, w, h);
+}
+
+void quit()
+{
+	Uint32 fp100s_aver = fp10s_acc*10/fp10s_acc_samples;
+	printf("\naverlage fps: %3d.%2d\n", fp100s_aver/100, fp100s_aver%100);
+	SDL_Quit();
+}
+
+void loop_sdl(Raytracer &rt, Camera &cam)
+{
+	SDL_Surface *screen;
+	Float *render_buffer;
+
+	pyrit_verbosity = 0;
+	render_buffer = (Float *) malloc(w*h*3*sizeof(Float));
+
+	if( SDL_Init(SDL_INIT_VIDEO) < 0 ) {
+		fprintf(stderr, "Couldn't initialize SDL: %s\n", SDL_GetError());
+		exit(1);
+	}
+	
+	atexit(quit);
+	
+	screen = SDL_SetVideoMode(w, h, 32, SDL_SWSURFACE|SDL_DOUBLEBUF|SDL_RESIZABLE);
+	if ( screen == NULL ) {
+		fprintf(stderr, "Unable to set video mode: %s\n", SDL_GetError());
+		exit(1);
+	}
+
+	SDL_Event event;
+	bool quit = false;
+	Float roty = 0.0, rotx = 0.0, move = 0.0;
+	while (!quit)
+	{
+		while (SDL_PollEvent(&event))
+		{
+			switch (event.type) {
+				case SDL_VIDEORESIZE:
+					w = event.resize.w;
+					h = event.resize.h;
+					render_buffer = (Float *) realloc(render_buffer, w*h*3*sizeof(Float));
+					screen = SDL_SetVideoMode(w, h, 32, SDL_HWSURFACE|SDL_DOUBLEBUF|SDL_RESIZABLE);
+					break;
+				case SDL_KEYDOWN:
+					if (event.key.keysym.sym == SDLK_ESCAPE) {
+						quit = true;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_LEFT) {
+						roty = -0.01;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_RIGHT) {
+						roty = +0.01;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_DOWN) {
+						rotx = +0.01;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_UP) {
+						rotx = -0.01;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_w) {
+						move = +0.5;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_s) {
+						move = -0.5;
+						break;
+					}
+					break;
+				case SDL_KEYUP:
+					if (event.key.keysym.sym == SDLK_LEFT || event.key.keysym.sym == SDLK_RIGHT) {
+						roty = 0.0;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_UP || event.key.keysym.sym == SDLK_DOWN) {
+						rotx = 0.0;
+						break;
+					}
+					if (event.key.keysym.sym == SDLK_w || event.key.keysym.sym == SDLK_s) {
+							move = 0.0;
+							break;
+						}
+					break;
+				case SDL_QUIT:
+					quit = true;
+			}
+		}
+		cam.rotate(Quaternion(cos(roty),0,sin(roty),0).normalize());
+		cam.rotate(Quaternion(cos(rotx),cam.u[0]*sin(rotx),0,cam.u[2]*sin(rotx)).normalize());
+		cam.u.y = 0;
+		cam.u.normalize();
+		cam.move(move,0,0);
+		update(rt, screen, render_buffer);
+	}
+	free(render_buffer);
+}