aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--cmd/demo/main.ha114
-rw-r--r--sdl2/timer.ha32
-rw-r--r--sdl2/video.ha13
3 files changed, 115 insertions, 44 deletions
diff --git a/cmd/demo/main.ha b/cmd/demo/main.ha
index f7ece50..43aea33 100644
--- a/cmd/demo/main.ha
+++ b/cmd/demo/main.ha
@@ -5,11 +5,21 @@ use sdl2;
use sdl2::image;
use strings;
+type texture = struct {
+ tex: *sdl2::texture,
+ w: int,
+ h: int,
+};
+
type state = struct {
- hare: *sdl2::texture,
- cat: *sdl2::texture,
+ window: *sdl2::window,
+ render: *sdl2::renderer,
+ hare: texture,
+ cat: texture,
hare_x: int,
hare_y: int,
+ hare_dx: int,
+ hare_dy: int,
cat_x: int,
cat_y: int,
};
@@ -41,67 +51,83 @@ export fn main() void = {
defer sdl2::destroy_renderer(render);
let state = state {
- hare = {
- const path = strings::to_c("mascot.jpg");
- defer free(path);
- yield match (image::load_texture(render, path)) {
- case let tex: *sdl2::texture =>
- yield tex;
- case null =>
- fmt::fatal("sdl2::image::load_texture failed for mascot.jpg");
- };
- },
- cat = {
- const path = strings::to_c("cat.png");
- defer free(path);
- yield match (image::load_texture(render, path)) {
- case let tex: *sdl2::texture =>
- yield tex;
- case null =>
- fmt::fatal("sdl2::image::load_texture failed for cat.png");
- };
- },
+ window = win,
+ render = render,
+ hare = load_texture(render, "mascot.jpg"),
+ cat = load_texture(render, "cat.png"),
hare_x = 100,
hare_y = 100,
+ hare_dx = 2,
+ hare_dy = 2,
...
};
- defer sdl2::destroy_texture(state.hare);
- defer sdl2::destroy_texture(state.cat);
-
- draw_frame(&state, render);
+ defer sdl2::destroy_texture(state.hare.tex);
+ defer sdl2::destroy_texture(state.cat.tex);
let ev = sdl2::event { ... };
- for (sdl2::wait_event(&ev) == 1) {
- switch (ev.event_type) {
+ for (true) {
+ if (sdl2::poll_event(&ev) == 1) switch (ev.event_type) {
case event_type::QUIT =>
break;
case => void;
};
+
+ update(&state);
+ draw(&state);
+
+ sdl2::delay(1000 / 60);
};
os::exit(0); // https://todo.sr.ht/~sircmpwn/hare/525
};
-fn draw_frame(state: *state, render: *sdl2::renderer) void = {
- sdl2::set_render_draw_color(render, 50, 50, 50, 255);
- sdl2::render_clear(render);
- draw_tex(render, state.cat, state.cat_x, state.cat_y);
- draw_tex(render, state.hare, state.hare_x, state.hare_y);
- sdl2::render_present(render);
+fn load_texture(render: *sdl2::renderer, path: str) texture = {
+ const path = strings::to_c(path);
+ defer free(path);
+
+ const tex = match (image::load_texture(render, path)) {
+ case let tex: *sdl2::texture =>
+ yield tex;
+ case null =>
+ fmt::fatal("sdl2::image::load_texture failed for cat.png");
+ };
+
+ let w = 0, h = 0;
+ sdl2::query_texture(tex, null, null, &w, &h);
+ return texture {
+ tex = tex,
+ w = w,
+ h = h,
+ };
};
-fn draw_tex(
- render: *sdl2::renderer,
- tex: *sdl2::texture,
- x: int,
- y: int,
-) void = {
+fn update(state: *state) void = {
let width = 0, height = 0;
- sdl2::query_texture(tex, null, null, &width, &height);
- sdl2::render_copy(render, tex, null, &sdl2::rect {
+ sdl2::get_window_size(state.window, &width, &height);
+
+ state.hare_x += state.hare_dx;
+ state.hare_y += state.hare_dy;
+ if (state.hare_x <= 0 || state.hare_x + state.hare.w >= width) {
+ state.hare_dx = -state.hare_dx;
+ };
+ if (state.hare_y <= 0 || state.hare_y + state.hare.h >= height) {
+ state.hare_dy = -state.hare_dy;
+ };
+};
+
+fn draw(state: *state) void = {
+ sdl2::set_render_draw_color(state.render, 50, 50, 50, 255);
+ sdl2::render_clear(state.render);
+ draw_tex(state, &state.hare, state.hare_x, state.hare_y);
+ draw_tex(state, &state.cat, state.cat_x, state.cat_y);
+ sdl2::render_present(state.render);
+};
+
+fn draw_tex(state: *state, tex: *texture, x: int, y: int) void = {
+ sdl2::render_copy(state.render, tex.tex, null, &sdl2::rect {
x = x,
y = y,
- w = width,
- h = height,
+ w = tex.w,
+ h = tex.h,
});
};
diff --git a/sdl2/timer.ha b/sdl2/timer.ha
new file mode 100644
index 0000000..da958b6
--- /dev/null
+++ b/sdl2/timer.ha
@@ -0,0 +1,32 @@
+// Get the number of milliseconds since SDL library initialization.
+//
+// This value wraps if the program runs for more than ~49 days.
+//
+// Returns an unsigned 32-bit value representing the number of milliseconds
+// since the SDL library initialized.
+export @symbol("SDL_GetTicks") fn getticks() u32;
+
+// Get the current value of the high resolution counter.
+//
+// This function is typically used for profiling.
+//
+// The counter values are only meaningful relative to each other. Differences
+// between values can be converted to times by using
+// [[getperformancefrequency]].
+//
+// Returns the current counter value.
+export @symbol("SDL_GetPerformanceCounter") fn getperformancecounter() u64;
+
+// Get the count per second of the high resolution counter.
+//
+// Returns a platform-specific count per second.
+export @symbol("SDL_GetPerformanceFrequency") fn getperformancefrequency() u64;
+
+// Wait a specified number of milliseconds before returning.
+//
+// This function waits a specified number of milliseconds before returning. It
+// waits at least the specified time, but possibly longer due to OS
+// scheduling.
+export @symbol("SDL_Delay") fn delay(ms: u32) void;
+
+// TODO: Timers
diff --git a/sdl2/video.ha b/sdl2/video.ha
index e12ca12..e6dfa58 100644
--- a/sdl2/video.ha
+++ b/sdl2/video.ha
@@ -71,3 +71,16 @@ export @symbol("SDL_CreateWindow") fn create_window(title: const *char,
// Destroy a window.
export @symbol("SDL_DestroyWindow") fn destroy_window(window: *window) void;
+
+// Get the size of a window's client area.
+//
+// Null may safely be passed as the 'w' or 'h' parameter if the width or
+// height value is not desired.
+//
+// The window size in screen coordinates may differ from the size in pixels, if
+// the window was created with `ALLOW_HIGHDPI` on a platform with high-dpi
+// support (e.g. iOS or macOS). Use [[gl_getdrawablesize]],
+// [[vulkan_getdrawablesize]], or [[getrendereroutputsize]] to get the real
+// client area size in pixels.
+export @symbol("SDL_GetWindowSize") fn get_window_size(window: *window,
+ w: nullable *int, h: nullable *int) void;