summaryrefslogtreecommitdiff
path: root/gfx-iso/app/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'gfx-iso/app/main.c')
-rw-r--r--gfx-iso/app/main.c185
1 files changed, 185 insertions, 0 deletions
diff --git a/gfx-iso/app/main.c b/gfx-iso/app/main.c
new file mode 100644
index 0000000..fa5a76b
--- /dev/null
+++ b/gfx-iso/app/main.c
@@ -0,0 +1,185 @@
1#include "app.h"
2#include "checkerboard.h"
3#include "isogfx-demo.h"
4
5#include <isogfx/isogfx.h>
6
7#include <gfx/gfx.h>
8#include <gfx/gfx_app.h>
9#include <gfx/render_backend.h>
10#include <gfx/renderer.h>
11#include <gfx/scene.h>
12#include <gfx/util/geometry.h>
13#include <gfx/util/shader.h>
14
15#include <assert.h>
16#include <stdbool.h>
17#include <stdlib.h>
18
19static const int SCREEN_WIDTH = 1408;
20static const int SCREEN_HEIGHT = 960;
21
22typedef struct State {
23 Gfx* gfx;
24 IsoGfx* iso;
25 IsoGfxApp app;
26 Texture* screen_texture;
27 Scene* scene;
28} State;
29
30static bool init(const GfxAppDesc* desc, void** app_state) {
31 State* state = calloc(1, sizeof(State));
32 if (!state) {
33 return false;
34 }
35
36 if (!(state->iso = isogfx_new(&(IsoGfxDesc){
37 .screen_width = SCREEN_WIDTH, .screen_height = SCREEN_HEIGHT}))) {
38 goto cleanup;
39 }
40 // if (!make_checkerboard_app(state->iso, &state->app)) {
41 // goto cleanup;
42 // }
43 if (!make_demo_app(state->iso, &state->app)) {
44 goto cleanup;
45 }
46 if (!(state->gfx = gfx_init())) {
47 goto cleanup;
48 }
49 RenderBackend* render_backend = gfx_get_render_backend(state->gfx);
50
51 if (!(state->screen_texture = gfx_make_texture(
52 render_backend, &(TextureDesc){
53 .width = SCREEN_WIDTH,
54 .height = SCREEN_HEIGHT,
55 .dimension = Texture2D,
56 .format = TextureSRGBA8,
57 .filtering = NearestFiltering,
58 .wrap = ClampToEdge,
59 .mipmaps = false}))) {
60 goto cleanup;
61 }
62
63 ShaderProgram* shader = gfx_make_view_texture_shader(render_backend);
64 if (!shader) {
65 goto cleanup;
66 }
67
68 Geometry* geometry = gfx_make_quad_11(render_backend);
69 if (!geometry) {
70 goto cleanup;
71 }
72
73 MaterialDesc material_desc = (MaterialDesc){.num_uniforms = 1};
74 material_desc.uniforms[0] = (ShaderUniform){
75 .type = UniformTexture,
76 .value.texture = state->screen_texture,
77 .name = sstring_make("Texture")};
78 Material* material = gfx_make_material(&material_desc);
79 if (!material) {
80 return false;
81 }
82
83 const MeshDesc mesh_desc =
84 (MeshDesc){.geometry = geometry, .material = material, .shader = shader};
85 Mesh* mesh = gfx_make_mesh(&mesh_desc);
86 if (!mesh) {
87 goto cleanup;
88 }
89
90 SceneObject* object = gfx_make_object();
91 if (!object) {
92 goto cleanup;
93 }
94 gfx_add_object_mesh(object, mesh);
95
96 state->scene = gfx_make_scene();
97 SceneNode* node = gfx_make_object_node(object);
98 SceneNode* root = gfx_get_scene_root(state->scene);
99 gfx_set_node_parent(node, root);
100
101 *app_state = state;
102 return true;
103
104cleanup:
105 if (state->gfx) {
106 gfx_destroy(&state->gfx);
107 }
108 free(state);
109 return false;
110}
111
112static void shutdown(void* app_state) {
113 assert(app_state);
114 State* state = (State*)(app_state);
115
116 if (state->app.state) {
117 assert(state->iso);
118 (*state->app.shutdown)(state->iso, state->app.state);
119 }
120 isogfx_del(&state->iso);
121 gfx_destroy(&state->gfx);
122 free(app_state);
123}
124
125static void update(void* app_state, double t, double dt) {
126 assert(app_state);
127 State* state = (State*)(app_state);
128
129 assert(state->app.update);
130 (*state->app.update)(state->iso, state->app.state, t, dt);
131}
132
133static void render(void* app_state) {
134 assert(app_state);
135 State* state = (State*)(app_state);
136
137 assert(state->app.render);
138 (*state->app.render)(state->iso, state->app.state);
139
140 const Pixel* screen = isogfx_get_screen_buffer(state->iso);
141 assert(screen);
142 gfx_update_texture(
143 state->screen_texture, &(TextureDataDesc){.pixels = screen});
144
145 RenderBackend* render_backend = gfx_get_render_backend(state->gfx);
146 Renderer* renderer = gfx_get_renderer(state->gfx);
147
148 gfx_start_frame(render_backend);
149 gfx_render_scene(
150 renderer, &(RenderSceneParams){
151 .mode = RenderDefault, .scene = state->scene, .camera = 0});
152 gfx_end_frame(render_backend);
153}
154
155static void resize(void* app_state, int width, int height) {
156 assert(app_state);
157 State* state = (State*)(app_state);
158
159 RenderBackend* render_backend = gfx_get_render_backend(state->gfx);
160 gfx_set_viewport(render_backend, width, height);
161}
162
163int main(int argc, const char** argv) {
164 const int initial_width = SCREEN_WIDTH;
165 const int initial_height = SCREEN_HEIGHT;
166 const int max_fps = 60;
167
168 gfx_app_run(
169 &(GfxAppDesc){
170 .argc = argc,
171 .argv = argv,
172 .width = initial_width,
173 .height = initial_height,
174 .max_fps = max_fps,
175 .update_delta_time = max_fps > 0 ? 1.0 / (double)max_fps : 0.0,
176 .title = "Isometric Renderer"},
177 &(GfxAppCallbacks){
178 .init = init,
179 .update = update,
180 .render = render,
181 .resize = resize,
182 .shutdown = shutdown});
183
184 return 0;
185}