summaryrefslogtreecommitdiff
path: root/3de.c
blob: 9a5295fc70f76375ea9fcd9aff08f1da839cdf10 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
#include "config.h"
#include "maths.h"
#include "memory.h"
#include "plat.h"
#include "render.h"
#include "tile.h"
#include "torus.h"

#include <stdio.h>

void draw_spinny(Renderer* r, Colour c) {
	static int a = 0;
	int y; int x = y = 100 << fbits;
	x -= sin_table[a & sin_table_mask] * 10;
	y += cos_table[a & sin_table_mask] * 10;
	ren_point(r, c, x >> fbits, y >> fbits);
	a += 20;
}

void draw_torus(Renderer* r) {
	static int a = 0;
	Bitmap tex = { (Colour*)tile_pixels, 16, 16 };
	const int pc = sizeof torus_points / sizeof *torus_points;
	int asp = (r->clip.w << fbits) / r->clip.h;
	int p[4 * 3] = { 0, 0, 5 << fbits, f1, 0, 0, 0, f1, 0, 0, 0, f1 }, * wp;
	int v[8 * 3];
	int i, j;
	mtx_push_trans(p);
	mtx_push_rot_x(a);
	mtx_push_rot_y(a);
	mtx_push_rot_z(a);
	for (i = 0; i < pc; i += 3 * 5) {
		for (j = 0; j < 3; j++) {
			wp = &p[j * 4];
			vec_cpy(wp, &torus_points[i + j * 5], 3);
			mtx_apply(mtx_peek(), wp);
			persp(wp, asp);
			ndc2clip((int*)&r->clip, wp);
		}
		for (j = 0; j < 3; j++) {
			int j8 = j * 8;
			vec_cpy(&v[j8], &p[j * 4], 3);
			v[j8 + 3] = torus_points[i + j * 5];
			v[j8 + 4] = torus_points[i + j * 5 + 1];
			v[j8 + 5] = f1;
			v[j8 + 6] = f1;
			v[j8 + 7] = f1;
		}
		ren_tri(r, &v[0], &v[8], &v[16], &tex);
	}
	mtx_popn(4);
	a += 3;
}

void draw_tri(Renderer* r, int x, int y) {
	Bitmap t = { (Colour*)tile_pixels, 16, 16 };
	int v0[] = { 100, 100, 0, 0,  0,    f1, 0,  0  };
	int v1[] = { 200, 200, 0, f1, f1/2, 0,  f1, 0  };
	int v2[] = { 150, 300, 0, 0,  f1,   0,  0,  f1 };
	v1[0] = x;
	v1[1] = y;
	ren_tri(r, v0, v1, v2, &t);
}

int entrypoint(int argc, const char** argv, Arena* a) {
	App* app;
	Renderer r = { 0 };
	Heap h;
	FPS f;
	char buf[32];
	int* depth = 0;
	Colour blue = make_aliceblue();
	(void)argc;
	(void)argv;
	init_maths();
	init_heap(
		&h,
		arena_alloc(a, app_memory_size),
		app_memory_size
	);
	app = new_app(&h, 640, 480, "3D Engine");
	if (!app) return app->err;
	init_fps(&f, 20);
	depth = heap_alloc(&h, max_vp_w * max_vp_h * sizeof *depth);
	if (!depth) {
		print_err("Out of memory.\n");
		return error_out_of_memory;
	}
	while (app->o) {
		fps_begin(&f);
		while (f.now >= f.next) {
			app_begin(app);
			ren_begin(&r, app->fb, depth, app->w, app->h);
				ren_clear(&r);
				ren_cleard(&r, f1 * 300);
				sprintf(buf, "FPS: %d", app->fps);
				ren_text(&r, blue, 3, 3,  buf);
				sprintf(buf, "CAP: %d", f.fps);
				ren_text(&r, blue, 3, 13, buf);
				sprintf(buf, "MOUSE: %d, %d", app->mx, app->my);
				ren_text(&r, blue, 3, 23, buf);
				draw_torus(&r);
				draw_tri(&r, app->mx, app->my);
			ren_end(&r);
			app_end(app);
			fps_update(&f);
		}
		fps_end(&f);
	}
	deinit_app(app);
	return 0;
}