--- /dev/null
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include "screen.h"
+#include "demo.h"
+
+static int init(void);
+static void destroy(void);
+static void start(long trans_time);
+static void stop(long trans_time);
+static void draw(void);
+
+static struct screen scr = {
+ "console",
+ init,
+ destroy,
+ start,
+ stop,
+ draw
+};
+
+static void *saved_fb;
+static int fbsize;
+static long trans_start, trans_dur;
+
+struct screen *console_screen(void)
+{
+ return &scr;
+}
+
+static int init(void)
+{
+ fbsize = fb_width * fb_height * fb_depth / 8;
+
+ if(!(saved_fb = malloc(fbsize))) {
+ perror("failed to allocate memory");
+ return -1;
+ }
+ memcpy(saved_fb, fb_pixels, fbsize);
+ return 0;
+}
+
+static void destroy(void)
+{
+ memcpy(fb_pixels, saved_fb, fbsize);
+ free(saved_fb);
+}
+
+static void start(long trans_time)
+{
+}
+
+static void stop(long trans_time)
+{
+ trans_start = time_msec;
+ trans_dur = trans_time;
+}
+
+static void draw(void)
+{
+ int i, pixsz = fb_depth / 8;
+ long elapsed, offs, rem;
+ unsigned char *dptr = fb_pixels;
+ unsigned char *sptr = saved_fb;
+
+ if(!trans_start) {
+ return;
+ }
+ printf("console draw\n");
+
+ elapsed = time_msec - trans_start;
+ offs = fb_width * elapsed / trans_dur;
+ rem = fb_width - offs;
+
+ for(i=0; i<fb_height; i++) {
+ if(offs > 0) {
+ memset(dptr, 0, offs * pixsz);
+ }
+ if(rem > 0) {
+ memcpy(dptr + offs * pixsz, sptr, rem * pixsz);
+ }
+
+ dptr += fb_width * pixsz;
+ sptr += fb_width * pixsz;
+ }
+}
--- /dev/null
+#ifndef DEMO_H_
+#define DEMO_H_
+
+void *fb_pixels;
+int fb_width, fb_height;
+int fb_depth;
+
+long time_msec;
+
+#endif /* DEMO_H_ */
#include <string.h>
#include "fbgfx.h"
#include "fbevents.h"
-#include "tunnel.h"
#include "timer.h"
-
-unsigned long start_msec, time_msec, num_frames;
+#include "screen.h"
+#include "screen.h"
+#include "demo.h"
static void keyboard(int key, int pressed, void *cls);
static void mouse(int bn, int pressed, int x, int y, void *cls);
static void motion(int x, int y, void *cls);
-static void *vmem;
-static int xsz, ysz, depth;
+static long start_msec, num_frames;
static int quit;
int i, trybpp[] = {32, 24, 16, 0};
fbgfx_save_video_mode();
- fbgfx_get_video_mode(&xsz, &ysz, &depth);
+ fbgfx_get_video_mode(&fb_width, &fb_height, &fb_depth);
for(i=0; trybpp[i]; i++) {
- if(!(vmem = fbgfx_set_video_mode(xsz, ysz, trybpp[i]))) {
+ if(!(fb_pixels = fbgfx_set_video_mode(fb_width, fb_height, trybpp[i]))) {
continue;
}
- fbgfx_get_video_mode(&xsz, &ysz, &depth);
- if(depth == trybpp[i]) {
+ fbgfx_get_video_mode(&fb_width, &fb_height, &fb_depth);
+ if(fb_depth == trybpp[i]) {
break;
}
- fprintf(stderr, "failed to set color depth: %dbpp\n", trybpp[i]);
+ fprintf(stderr, "failed to set color fb_depth: %dbpp\n", trybpp[i]);
}
if(trybpp[i] == 0) {
- fprintf(stderr, "no usable color depths found\n");
+ fprintf(stderr, "no usable color fb_depths found\n");
goto end;
}
fbev_mbutton(mouse, 0);
fbev_mmotion(motion, 0);
- if(init_tunnel(xsz, ysz, depth) == -1) {
+ if(scr_init() == -1) {
goto end;
}
+ scr_change(scr_lookup("console"), 0);
+ scr_change(scr_lookup("tunnel"), 2000);
start_msec = get_time_msec();
for(;;) {
time_msec = get_time_msec() - start_msec;
- draw_tunnel(vmem);
+ scr_update();
+ scr_draw();
++num_frames;
}
time_msec = get_time_msec() - start_msec;
end:
- destroy_tunnel();
+ scr_shutdown();
fbev_shutdown();
fbgfx_restore_video_mode();
if(num_frames && time_msec) {
--- /dev/null
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include "screen.h"
+#include "demo.h"
+
+struct screen *console_screen(void);
+struct screen *tunnel_screen(void);
+
+#define NUM_SCR 2
+static struct screen *scr[NUM_SCR];
+
+static struct screen *cur, *prev, *next;
+static long trans_start, trans_dur;
+
+int scr_init(void)
+{
+ int i;
+
+ if(!(scr[0] = console_screen())) {
+ return -1;
+ }
+ if(!(scr[1] = tunnel_screen())) {
+ return -1;
+ }
+
+ for(i=0; i<NUM_SCR; i++) {
+ if(scr[i]->init() == -1) {
+ return -1;
+ }
+ }
+ return 0;
+}
+
+void scr_shutdown(void)
+{
+ int i;
+ for(i=0; i<NUM_SCR; i++) {
+ scr[i]->shutdown();
+ }
+}
+
+void scr_update(void)
+{
+ if(prev) { /* we're in the middle of a transition */
+ long interval = time_msec - trans_start;
+ if(interval >= trans_dur) {
+ prev = 0;
+ cur = next;
+ next = 0;
+ }
+ }
+}
+
+void scr_draw(void)
+{
+ if(cur) cur->draw();
+}
+
+struct screen *scr_lookup(const char *name)
+{
+ int i;
+ for(i=0; i<NUM_SCR; i++) {
+ if(strcmp(scr[i]->name, name) == 0) {
+ return scr[i];
+ }
+ }
+ return 0;
+}
+
+int scr_change(struct screen *s, long trans_time)
+{
+ if(s == cur) return 0;
+
+ if(trans_time && cur) {
+ trans_dur = trans_time / 2; /* half for each part transition out then in */
+ trans_start = time_msec;
+
+ prev = cur;
+ next = s;
+ } else {
+ cur = s;
+ }
+ return 0;
+}
--- /dev/null
+#ifndef SCREEN_H_
+#define SCREEN_H_
+
+struct screen {
+ char *name;
+
+ int (*init)(void);
+ void (*shutdown)(void);
+
+ void (*start)(long trans_time);
+ void (*stop)(long trans_time);
+
+ void (*draw)(void);
+};
+
+int scr_init(void);
+void scr_shutdown(void);
+
+void scr_update(void);
+void scr_draw(void);
+
+struct screen *scr_lookup(const char *name);
+int scr_change(struct screen *s, long trans_time);
+
+#endif /* SCREEN_H_ */
#include <assert.h>
#include <imago2.h>
#include "tpool.h"
-#include "tunnel.h"
+#include "demo.h"
+#include "screen.h"
#define TEX_FNAME "data/grid.png"
#define TEX_USCALE 4
#define USCALE 2
#define VSCALE 1
-extern unsigned long time_msec;
+static int init(void);
+static void destroy(void);
+static void start(long trans_time);
+static void stop(long trans_time);
+static void draw(void);
static void (*draw_tunnel_range)(void*, int, int);
static int count_bits(unsigned int x);
static int count_zeros(unsigned int x);
+static struct screen scr = {
+ "tunnel",
+ init,
+ destroy,
+ start,
+ stop,
+ draw
+};
+
static int xsz, ysz, vxsz, vysz;
static unsigned int *tunnel_map;
static unsigned char *tunnel_fog;
static struct thread_pool *tpool;
-int init_tunnel(int x, int y, int bpp)
+struct screen *tunnel_screen(void)
+{
+ return &scr;
+}
+
+
+static int init(void)
{
int i, j, n;
unsigned int *tmap;
unsigned char *fog;
- float aspect = (float)x / (float)y;
+ float aspect = (float)fb_width / (float)fb_height;
- switch(bpp) {
+ switch(fb_depth) {
case 16:
draw_tunnel_range = draw_tunnel_range16;
break;
draw_tunnel_range = draw_tunnel_range32;
break;
default:
- fprintf(stderr, "unsupported color depth: %d\n", bpp);
+ fprintf(stderr, "unsupported color depth: %d\n", fb_depth);
return -1;
}
- xsz = x;
- ysz = y;
+ xsz = fb_width;
+ ysz = fb_height;
vxsz = xsz / USCALE;
vysz = ysz / VSCALE;
return 0;
}
-void destroy_tunnel(void)
+static void destroy(void)
{
tpool_destroy(tpool);
free(tunnel_map);
free(tunnel_fog);
}
+static void start(long trans_time)
+{
+}
+
+static void stop(long trans_time)
+{
+}
+
#define NUM_WORK_ITEMS 32
static struct work {
draw_tunnel_range(w->pixels, w->starty, w->num_lines);
}
-void draw_tunnel(void *pixels)
+static void draw(void)
{
int i, num_lines = vysz / NUM_WORK_ITEMS;
for(i=0; i<NUM_WORK_ITEMS; i++) {
- work[i].pixels = pixels;
+ work[i].pixels = fb_pixels;
work[i].starty = i * num_lines;
work[i].num_lines = num_lines;
+++ /dev/null
-#ifndef TUNNEL_H_
-#define TUNNEL_H_
-
-int init_tunnel(int x, int y, int bpp);
-void destroy_tunnel(void);
-void draw_tunnel(void *pixels);
-
-#endif /* TUNNEL_H_ */