examples

Toy examples in single C files.
git clone git://henryandlizzy.uk/examples
Log | Files | Refs

commit 37e6ac5b19048e4bd2e0a220cce26fb1ab5da611
parent cf735b6b145557a74db354879fc3c94593106b3d
Author: Henry Wilson <henry@henryandlizzy.uk>
Date:   Sat, 22 Jun 2024 11:06:50 +0100

sdl-gl: Drag objects around

Diffstat:
Msrc/sdl-gl.cpp | 82++++++++++++++++++++++++++++++++++++++++++++++++++++++++++---------------------
1 file changed, 60 insertions(+), 22 deletions(-)

diff --git a/src/sdl-gl.cpp b/src/sdl-gl.cpp @@ -8,13 +8,12 @@ #include "coroutine_owner.hpp" +#include <algorithm> #include <cassert> #include <exception> #include <numbers> #include <print> - -#define ARRAY_SIZE(a) (sizeof(a) / sizeof(*(a))) -#define ARRAY_SSIZE(a) ((ssize_t)ARRAY_SIZE(a)) +#include <vector> extern "C" char const* __asan_default_options() { return "detect_leaks=0"; } @@ -174,28 +173,38 @@ point pan = {1, 0}; point mouse_pos; +struct object +{ + point pos; + rgb col; +} objs[] = { + {{0, 0}, {.7,.2,.2}}, + {{4, 0}, {.2,.7,.2}}, + {{0, 5}, {.2,.2,.7}}, +}; + +std::vector<point> shape; + void presentScene(void) { static double turns = 0; turns += 1./60/4; rotor r = rotor::angle(turns); - static point const square[4] = {{-1, -1}, {-1, 1}, {1, -1}, {1, 1}}; - point objs[] = {{0, 0}, {4, 0}, {0, 5}}; float x_scale = (float)screen_height / screen_width; glClearColor(0, 0, 0, 1); glClear(GL_COLOR_BUFFER_BIT); circle mouse_area{mouse_pos, 1}; - for (auto op : objs) { - if (mouse_area.colliding(op)) - glColor3d(1,1,0); + for (auto& op : objs) { + if (mouse_area.colliding(op.pos)) + glColor3d(op.col.r + .25,op.col.g + .25,op.col.b + .25); else - glColor3d(.5,.5,.5); + glColor3f(op.col.r, op.col.g, op.col.b); - glBegin(GL_TRIANGLE_STRIP); - for (auto& p : square) { - auto pp = (p * r + pan + op) * scale; + glBegin(GL_TRIANGLE_FAN); + for (auto& p : shape) { + auto pp = (p * r + pan + op.pos) * scale; glVertex2f(pp.x * x_scale, pp.y); } glEnd(); @@ -249,20 +258,41 @@ coroutine_task mouse_task() for (;;) { SDL_MouseButtonEvent const& e = co_await click_event; - if (e.button != SDL_BUTTON_RIGHT) - continue; - point drag_pos = pan - mouse_to_local(e.x, e.y); - - for (;;) + switch (e.button) + { + case SDL_BUTTON_RIGHT: { - SDL_Event const& e2 = co_await motion_or_release_event; - if (e2.type == SDL_MOUSEMOTION) - pan = drag_pos + mouse_to_local(e2.motion.x, e2.motion.y); - else if (auto& b = e2.button; b.button == SDL_BUTTON_RIGHT) + for (;;) + { + SDL_Event const& e2 = co_await motion_or_release_event; + if (e2.type == SDL_MOUSEMOTION) + pan = drag_pos + mouse_to_local(e2.motion.x, e2.motion.y); + else if (auto& b = e2.button; b.button == SDL_BUTTON_RIGHT) + break; + } + break; + } + case SDL_BUTTON_LEFT: + { + circle mouse_area{mouse_pos, 1}; + auto obj = std::ranges::find_if(objs, [drag_pos, mouse_area](auto const& o){return mouse_area.colliding(o.pos);}); + if (obj == std::end(objs)) break; + std::swap(obj->col.r, obj->col.g); + std::swap(obj->col.g, obj->col.b); + drag_pos = obj->pos - mouse_to_local(e.x, e.y); + for (;;) + { + SDL_Event const& e2 = co_await motion_or_release_event; + if (e2.type == SDL_MOUSEMOTION) + obj->pos = drag_pos + mouse_to_local(e2.motion.x, e2.motion.y); + else if (auto& b = e2.button; b.button == SDL_BUTTON_LEFT) + break; + } + break; + } } - } } @@ -322,8 +352,16 @@ void doInput() } } +void init_shape() +{ + shape.emplace_back(0,0); + for (int i = 0; i <= 8; ++i) + shape.push_back(point{1, 0} * rotor::angle((float)i / 8)); +} + int main() { + init_shape(); mouse_task(); initSDL(); atexit(SDL_Quit);