rev |
line source |
nuclear@4
|
1 #include <stdlib.h>
|
nuclear@4
|
2 #include <string.h>
|
nuclear@4
|
3 #include "rend.h"
|
nuclear@4
|
4 #include "player.h"
|
nuclear@4
|
5
|
nuclear@4
|
6 static void draw_tile(struct tile *tile);
|
nuclear@4
|
7
|
nuclear@4
|
8 static struct image fb;
|
nuclear@4
|
9
|
nuclear@4
|
10
|
nuclear@4
|
11 int init_renderer(void)
|
nuclear@4
|
12 {
|
nuclear@4
|
13 return 0;
|
nuclear@4
|
14 }
|
nuclear@4
|
15
|
nuclear@4
|
16 void shutdown_renderer(void)
|
nuclear@4
|
17 {
|
nuclear@4
|
18 }
|
nuclear@4
|
19
|
nuclear@4
|
20 void setup_renderer(unsigned char *pixels, int xsz, int ysz)
|
nuclear@4
|
21 {
|
nuclear@4
|
22 fb.xsz = xsz;
|
nuclear@4
|
23 fb.ysz = ysz;
|
nuclear@4
|
24 fb.pixels = pixels;
|
nuclear@4
|
25 }
|
nuclear@4
|
26
|
nuclear@4
|
27 #define MAX_Z 5
|
nuclear@4
|
28 #define LEFT 0
|
nuclear@4
|
29 #define CENTER 1
|
nuclear@4
|
30 #define RIGHT 2
|
nuclear@4
|
31
|
nuclear@4
|
32 #define CHR_TYPE 0
|
nuclear@4
|
33 #define CHR_SIDE 1
|
nuclear@4
|
34 #define CHR_STATE 2
|
nuclear@4
|
35 #define CHR_Z 3
|
nuclear@4
|
36
|
nuclear@4
|
37 void render_level(struct level *lvl, int px, int py, int pdir)
|
nuclear@4
|
38 {
|
nuclear@4
|
39 int i, j, dx, dy, backz, clear_start, clear_end;
|
nuclear@4
|
40 char cells[3][MAX_Z + 1];
|
nuclear@4
|
41 struct tileset *ts = &lvl->tileset;
|
nuclear@4
|
42 struct tile *tile_ceil, *tile_floor;
|
nuclear@4
|
43
|
nuclear@4
|
44 dx = pdir == DIR_EAST ? 1 : (pdir == DIR_WEST ? -1 : 0);
|
nuclear@4
|
45 dy = pdir == DIR_NORTH ? -1 : (pdir == DIR_SOUTH ? 1 : 0);
|
nuclear@4
|
46
|
nuclear@4
|
47 for(i=0; i<3; i++) { /* get 3 abreast cells ... */
|
nuclear@4
|
48 int xoffs = (1 - i) * dy;
|
nuclear@4
|
49 int yoffs = (i - 1) * dx;
|
nuclear@4
|
50
|
nuclear@4
|
51 for(j=0; j<MAX_Z + 1; j++) { /* ... for each depth */
|
nuclear@4
|
52 int x = px + xoffs + dx * j;
|
nuclear@4
|
53 int y = py + yoffs + dy * j;
|
nuclear@4
|
54
|
nuclear@4
|
55 cells[i][j] = level_cell(lvl, x, y);
|
nuclear@4
|
56 }
|
nuclear@4
|
57 }
|
nuclear@4
|
58
|
nuclear@4
|
59 /* draw floor and ceiling */
|
nuclear@4
|
60 tile_ceil = get_tile(ts, "ceil");
|
nuclear@4
|
61 tile_floor = get_tile(ts, "floor");
|
nuclear@4
|
62
|
nuclear@4
|
63 clear_start = tile_ceil ? tile_ceil->orig_y + tile_ceil->img.ysz : 0;
|
nuclear@4
|
64 clear_end = tile_floor ? tile_floor->orig_y : fb.ysz;
|
nuclear@4
|
65
|
nuclear@4
|
66 draw_tile(tile_ceil);
|
nuclear@4
|
67 draw_tile(tile_floor);
|
nuclear@4
|
68 memset(fb.pixels + clear_start * fb.xsz, 0, (clear_end - clear_start) * fb.xsz);
|
nuclear@4
|
69
|
nuclear@4
|
70 /* find where the back wall should go if it is within visual range
|
nuclear@4
|
71 * and draw it ...
|
nuclear@4
|
72 */
|
nuclear@4
|
73 backz = -1;
|
nuclear@4
|
74 for(i=1; i<MAX_Z + 1; i++) {
|
nuclear@4
|
75 if(cells[CENTER][i] == '#') {
|
nuclear@4
|
76 char name[] = "wcs "; /* wall-center-solid */
|
nuclear@4
|
77 backz = i;
|
nuclear@4
|
78 name[CHR_Z] = backz + '0' - 1;
|
nuclear@4
|
79 draw_tile(get_tile(ts, name));
|
nuclear@4
|
80 break;
|
nuclear@4
|
81 }
|
nuclear@4
|
82 }
|
nuclear@4
|
83 if(backz == -1) {
|
nuclear@4
|
84 char name[] = "wco "; /* wall-center-open */
|
nuclear@4
|
85 backz = MAX_Z;
|
nuclear@4
|
86 name[CHR_Z] = backz + '0' - 1;
|
nuclear@4
|
87 draw_tile(get_tile(ts, name));
|
nuclear@4
|
88 }
|
nuclear@4
|
89
|
nuclear@4
|
90 /* now render back to front */
|
nuclear@4
|
91 for(i=0; i<backz; i++) {
|
nuclear@4
|
92 int z = backz - i - 1;
|
nuclear@4
|
93 char name[] = "w---"; /* wall-<side>-<state>-<z> */
|
nuclear@4
|
94
|
nuclear@4
|
95 for(j=0; j<3; j++) {
|
nuclear@4
|
96 int state = 's';
|
nuclear@4
|
97
|
nuclear@4
|
98 if(j == CENTER) continue; /* no walls in the center */
|
nuclear@4
|
99
|
nuclear@4
|
100 if(cells[j][z] != '#') {
|
nuclear@4
|
101 state = 'o';
|
nuclear@4
|
102 /* if it's an open cell, then skip drawing if the next z is also open */
|
nuclear@4
|
103 if(z >= MAX_Z || cells[j][z + 1] != '#') continue;
|
nuclear@4
|
104 }
|
nuclear@4
|
105
|
nuclear@4
|
106 name[CHR_SIDE] = j == LEFT ? 'l' : 'r';
|
nuclear@4
|
107 name[CHR_STATE] = state;
|
nuclear@4
|
108 name[CHR_Z] = z + '0';
|
nuclear@4
|
109 draw_tile(get_tile(ts, name));
|
nuclear@4
|
110 }
|
nuclear@4
|
111 }
|
nuclear@4
|
112 }
|
nuclear@4
|
113
|
nuclear@4
|
114 static void draw_tile(struct tile *tile)
|
nuclear@4
|
115 {
|
nuclear@4
|
116 if(!tile) return;
|
nuclear@4
|
117
|
nuclear@4
|
118 blitkey(&fb, tile->orig_x, tile->orig_y, &tile->img, 31); /* TODO unhardcode key */
|
nuclear@4
|
119 }
|