jhhj
This commit is contained in:
Julia 2024-04-09 17:10:30 -05:00
parent c941f8b7fb
commit 879e8f2af2
12 changed files with 227 additions and 182 deletions

View file

@ -14,3 +14,16 @@ typedef uint_fast32_t u32f;
typedef uint64_t u64;
typedef uint_fast64_t u64f;
typedef int8_t i8;
typedef int_fast8_t i8f;
typedef int16_t i16;
typedef int_fast16_t i16f;
typedef int32_t i32;
typedef int_fast32_t i32f;
typedef int64_t i64;
typedef int_fast64_t i64f;

View file

@ -17,13 +17,19 @@ size_t delegate_size(size_t capacity)
return sizeof(void(*)(void *)) * capacity;
}
struct Delegate NewDelegate(size_t capacity)
bool NewDelegate(struct Delegate *d, size_t capacity)
{
return (struct Delegate) {
void (**events)(void *args) = malloc(delegate_size(capacity));
if (events == nullptr)
return false;
*d = (struct Delegate) {
.len = 0,
.capacity = capacity,
.events = malloc(delegate_size(capacity))
};
return true;
}
void Subscribe(struct Delegate *d, void (*event)(void *args))

View file

@ -13,7 +13,7 @@ struct Delegate {
void (**events)(void *args);
};
struct Delegate NewDelegate(size_t capacity);
bool NewDelegate(struct Delegate *d, size_t capacity);
void Subscribe(struct Delegate *d, void (*event)(void *args));

View file

@ -11,54 +11,48 @@
#define IO_BUF_SIZE 16
enum CtrlType {
enum InputType {
KEY,
AXIS,
JOYSTICK,
ESCAPE
};
struct Record {
u16 id;
struct Button {
u32 value;
bool is_down;
bool is_held;
bool is_up;
};
struct Axis {
i64 value;
};
struct Joystick {
i32 x;
i32 y;
};
struct InputRecord {
u16 bind;
u8 type;
union {
struct {
bool is_down;
} key;
struct {
u64 value;
} axis;
struct {
u32 x;
u32 y;
} joystick;
} data;
struct Button but;
struct Axis axis;
struct Joystick js;
};
struct timespec timestamp;
};
struct RecordBuffer {
struct Record records[IO_BUF_SIZE];
size_t count;
pthread_mutex_t mutex;
};
struct Axis {
struct InputAxis {
union {
struct {
u32 value;
u32 is_down : 1;
u32 is_up : 1;
} key;
struct {
u64 value;
} axis;
struct {
u32 x;
u32 y;
} joystick;
} data;
struct Button but;
struct Axis axis;
struct Joystick js;
};
struct timespec last_pressed;
struct timespec last_released;
@ -81,41 +75,44 @@ hashtype Hash(void *item, size_t size)
hashtype hash_id(u16f value, u8f type)
{
struct id {
u16 id;
u8 type;
};
struct id id = { value, type };
return Hash(&id, sizeof(struct id));
struct { u16 id; u8 type; } id = { value, type };
return Hash(&id, sizeof(id));
}
struct ctrl_dict {
size_t capacity;
size_t filled;
struct ctrl_bkt {
hashtype hash;
u16 value;
u8 type;
struct Axis *axis;
struct InputAxis *axis;
} *bkts;
};
struct ctrl_dict {
size_t capacity;
size_t filled;
struct ctrl_bkt *bkts;
};
struct Ctrl {
struct Controller {
struct ctrl_dict codes;
struct ctrl_dict binds;
struct InputAxis *axes;
struct RecordBuffer buf;
pthread_t thread;
struct {
struct InputRecord records[IO_BUF_SIZE];
size_t len;
} input_buf;
struct {
size_t indexes[IO_BUF_SIZE];
size_t len;
} pending_state_buf;
};
bool NewCtrl(struct Ctrl *ctrl, size_t code_cap, size_t bind_cap)
bool NewCtrl(struct Controller *ctrl, size_t code_cap, size_t bind_cap)
{
struct ctrl_bkt *code_bkts = calloc(code_cap, sizeof(struct ctrl_bkt));
struct ctrl_bkt *bind_bkts = calloc(bind_cap, sizeof(struct ctrl_bkt));
struct Axis *axes = calloc(code_cap, sizeof(struct Axis));
struct InputAxis *axes = calloc(code_cap, sizeof(struct InputAxis));
if (code_bkts == nullptr or bind_bkts == nullptr or axes == nullptr)
return false;
@ -124,7 +121,7 @@ bool NewCtrl(struct Ctrl *ctrl, size_t code_cap, size_t bind_cap)
code_bkts[i].axis = axes + i;
}
*ctrl = (struct Ctrl) {
*ctrl = (struct Controller) {
.codes = (struct ctrl_dict) {
.capacity = code_cap,
.filled = 0,
@ -135,19 +132,23 @@ bool NewCtrl(struct Ctrl *ctrl, size_t code_cap, size_t bind_cap)
.filled = 0,
.bkts = bind_bkts,
},
.axes = axes,
.buf = (struct RecordBuffer) {
.count = 0,
.mutex = PTHREAD_MUTEX_INITIALIZER,
.input_buf = {
.len = 0,
},
.pending_state_buf = {
.len = 0,
},
};
return true;
}
void FreeCtrl(struct Ctrl *ctrl)
void FreeCtrl(struct Controller *ctrl)
{
free(ctrl->codes.bkts);
free(ctrl->binds.bkts);
free(ctrl->axes);
}
struct ctrl_bkt *get_bkt(struct ctrl_dict *dict, size_t i)
@ -216,7 +217,7 @@ next:
return nullptr;
}
struct Axis *find_axis(struct ctrl_dict *dict, u16f value, u8f type)
struct InputAxis *find_axis(struct ctrl_dict *dict, u16f value, u8f type)
{
struct ctrl_bkt *bkt = find(dict, value, type);
if (bkt == nullptr)
@ -225,7 +226,7 @@ struct Axis *find_axis(struct ctrl_dict *dict, u16f value, u8f type)
return bkt->axis;
}
bool CtrlMap(struct Ctrl *ctrl, u16f code, u16f bind, u8f type)
bool CtrlMap(struct Controller *ctrl, u16f code, u16f bind, u8f type)
{
if (ctrl->codes.filled >= ctrl->codes.capacity or ctrl->binds.filled >= ctrl->binds.capacity) {
printf("fatal error");
@ -245,7 +246,7 @@ bool CtrlMap(struct Ctrl *ctrl, u16f code, u16f bind, u8f type)
return true;
}
struct Axis *CtrlGet(struct Ctrl *ctrl, u16f code, u8f type)
struct InputAxis *CtrlGet(struct Controller *ctrl, u16f code, u8f type)
{
struct ctrl_bkt *code_bkt = find(&ctrl->codes, code, type);
if (code_bkt == nullptr)
@ -254,53 +255,69 @@ struct Axis *CtrlGet(struct Ctrl *ctrl, u16f code, u8f type)
return code_bkt->axis;
}
void update_key(struct Axis *axis, struct Record *record)
void update_key(struct InputAxis *axis, struct InputRecord *rec)
{
if (record->data.key.is_down)
axis->last_pressed = record->timestamp;
else
axis->last_released = record->timestamp;
axis->data.key.is_down = record->data.key.is_down;
if (rec->but.is_down) {
axis->last_pressed = rec->timestamp;
axis->but.is_held = true;
} else {
axis->last_released = rec->timestamp;
axis->but.is_held = false;
}
void update_axis(struct Axis *axis, struct Record *record)
{
axis->data.axis.value = record->data.axis.value;
axis->last_pressed = record->timestamp;
axis->but.is_down |= rec->but.is_down;
axis->but.is_up |= rec->but.is_up;
}
void update_joystick(struct Axis *axis, struct Record *record)
void update_axis(struct InputAxis *axis, struct InputRecord *rec)
{
axis->data.joystick.x = record->data.joystick.x;
axis->data.joystick.y = record->data.joystick.y;
axis->last_pressed = record->timestamp;
axis->axis.value = rec->axis.value;
axis->last_pressed = rec->timestamp;
}
bool CtrlPoll(struct Ctrl *ctrl)
void update_joystick(struct InputAxis *axis, struct InputRecord *rec)
{
for (size_t i = 0; i < ctrl->buf.count; i++) {
struct Record *rec = &ctrl->buf.records[i];
axis->js.x = rec->js.x;
axis->js.y = rec->js.y;
struct Axis *axis = find_axis(&ctrl->binds, rec->id, rec->type);
if (axis == nullptr)
continue;
axis->last_pressed = rec->timestamp;
}
bool dispatch_update(struct InputAxis *axis, struct InputRecord *rec)
{
switch (rec->type) {
case KEY:
update_key(axis, rec);
break;
printf("axis:%hu\n", axis->but.is_down);
return true;
case AXIS:
update_axis(axis, rec);
break;
return true;
case JOYSTICK:
update_joystick(axis, rec);
break;
default:
return false;
}
}
ctrl->buf.count = 0;
return true;
}
return false;
}
bool CtrlPoll(struct Controller *ctrl)
{
for (size_t i = 0; i < ctrl->input_buf.len; i++) {
struct InputRecord *rec = &ctrl->input_buf.records[i];
printf("i:%hu\n", rec->bind);
struct InputAxis *axis = find_axis(&ctrl->binds, rec->bind, rec->type);
if (axis == nullptr)
continue;
if (!dispatch_update(axis, rec))
return false;
}
ctrl->input_buf.len = 0;
return true;
}

View file

@ -12,21 +12,22 @@
#define IO_BUF_SIZE 16
enum CtrlType {
enum InputType {
KEY,
AXIS,
JOYSTICK,
ESCAPE
};
struct Record {
u16 id;
struct InputRecord {
u16 bind;
u8 type;
union {
struct {
bool is_down;
} key;
bool is_up;
} button;
struct {
u64 value;
} axis;
@ -34,24 +35,25 @@ struct Record {
u32 x;
u32 y;
} joystick;
} data;
};
struct timespec timestamp;
};
struct RecordBuffer {
struct Record records[IO_BUF_SIZE];
struct InputRecord records[IO_BUF_SIZE];
size_t count;
pthread_mutex_t mutex;
};
struct Axis {
struct InputAxis {
union {
struct {
u32 value;
u32 is_down : 1;
u32 is_up : 1;
} key;
bool is_down;
bool is_held;
bool is_up;
} button;
struct {
u64 value;
} axis;
@ -59,7 +61,7 @@ struct Axis {
u32 x;
u32 y;
} joystick;
} data;
};
struct timespec last_pressed;
struct timespec last_released;
@ -86,7 +88,7 @@ struct ctrl_bkt {
hashtype hash;
u16 value;
u8 type;
struct Axis *axis;
struct InputAxis *axis;
};
struct ctrl_dict {
@ -95,20 +97,21 @@ struct ctrl_dict {
struct ctrl_bkt *bkts;
};
struct Ctrl {
struct Controller {
struct ctrl_dict codes;
struct ctrl_dict binds;
struct InputAxis *axes;
struct RecordBuffer buf;
pthread_t thread;
};
bool NewCtrl(struct Ctrl *ctrl, size_t code_cap, size_t bind_cap);
bool NewCtrl(struct Controller *ctrl, size_t code_cap, size_t bind_cap);
void FreeCtrl(struct Ctrl *ctrl);
void FreeCtrl(struct Controller *ctrl);
bool CtrlMap(struct Ctrl *ctrl, u16f code, u16f bind, u8f type);
bool CtrlMap(struct Controller *ctrl, u16f code, u16f bind, u8f type);
struct Axis *CtrlGet(struct Ctrl *ctrl, u16f code, u8f type);
struct InputAxis *CtrlGet(struct Controller *ctrl, u16f code, u8f type);
bool CtrlPoll(struct Ctrl *ctrl);
bool CtrlPoll(struct Controller *ctrl);

View file

@ -32,12 +32,12 @@ void *block_input(void *args_ptr)
return nullptr;
}
void StartInput(struct Ctrl *ctrl)
void StartInput(struct Controller *ctrl)
{
pthread_create(&ctrl->thread, nullptr, block_input, &ctrl->buf);
}
void JoinInput(struct Ctrl *ctrl)
void JoinInput(struct Controller *ctrl)
{
pthread_join(ctrl->thread, nullptr);
}

View file

@ -8,6 +8,6 @@
#include "ctrl.h"
#include "fumotris.h"
void StartInput(struct Ctrl *ctrl);
void StartInput(struct Controller *ctrl);
void JoinInput(struct Ctrl *ctrl);
void JoinInput(struct Controller *ctrl);

View file

@ -10,22 +10,17 @@
#include "winhandler.h"
#include "term.h"
#include <windows.h>
bool WindowsInit(struct Terminal *term)
{
if (!WinInitHandles())
return false;
printf("shid ");
if (!WinInitConsole()) {
printf("%u\n", GetLastError());
if (!WinInitConsole())
return false;
}
printf("console");
if (!WinGetRefreshRate(&term->refresh_rate))
return false;
printf("???");
return true;
}

View file

@ -39,9 +39,9 @@ bool WinInitConsole()
{
DWORD mode = ENABLE_EXTENDED_FLAGS
| ENABLE_PROCESSED_INPUT
| ENABLE_PROCESSED_OUTPUT
| ENABLE_MOUSE_INPUT
| ENABLE_WINDOW_INPUT
| ENABLE_VIRTUAL_TERMINAL_PROCESSING;
| ENABLE_WINDOW_INPUT;
return SetConsoleMode(win.input_handle, mode) != 0;
}
@ -62,34 +62,36 @@ bool WinGetRefreshRate(u16f *out)
return true;
}
void set_key_record(struct Record *record, KEY_EVENT_RECORD win_key)
void set_key_record(struct InputRecord *rec, KEY_EVENT_RECORD win_key)
{
record->type = KEY;
record->id = win_key.wVirtualKeyCode;
record->data.key.is_down = win_key.bKeyDown;
rec->type = KEY;
rec->bind = win_key.wVirtualKeyCode;
rec->button.is_down = win_key.bKeyDown;
rec->button.is_up = !win_key.bKeyDown;
if (win_key.wVirtualKeyCode == VK_ESCAPE)
record->type = ESCAPE;
rec->type = ESCAPE;
}
bool set_mouse_record(struct Record *record, MOUSE_EVENT_RECORD win_mouse)
bool set_mouse_record(struct InputRecord *rec, MOUSE_EVENT_RECORD win_mouse)
{
switch (win_mouse.dwEventFlags) {
case MOUSE_WHEELED:
record->type = AXIS;
record->id = 0;
record->data.axis.value = win_mouse.dwButtonState;
rec->type = AXIS;
rec->bind = 0;
rec->axis.value = win_mouse.dwButtonState;
break;
case MOUSE_HWHEELED:
record->type = AXIS;
record->id = 1;
record->data.axis.value = win_mouse.dwButtonState;
rec->type = AXIS;
rec->bind = 1;
rec->axis.value = win_mouse.dwButtonState;
break;
case MOUSE_MOVED:
record->type = JOYSTICK;
record->id = 0;
record->data.joystick.x = win_mouse.dwMousePosition.X;
record->data.joystick.y = win_mouse.dwMousePosition.Y;
rec->type = JOYSTICK;
rec->bind = 0;
rec->joystick.x = win_mouse.dwMousePosition.X;
rec->joystick.y = win_mouse.dwMousePosition.Y;
break;
default:
return false;
@ -97,19 +99,19 @@ bool set_mouse_record(struct Record *record, MOUSE_EVENT_RECORD win_mouse)
return true;
}
bool dispatch_record(struct Record *record, INPUT_RECORD win_record)
bool dispatch_record(struct InputRecord *rec, INPUT_RECORD win_rec)
{
switch (win_record.EventType) {
switch (win_rec.EventType) {
case KEY_EVENT:
set_key_record(record, win_record.Event.KeyEvent);
set_key_record(rec, win_rec.Event.KeyEvent);
break;
case MOUSE_EVENT:
return set_mouse_record(record, win_record.Event.MouseEvent);
return set_mouse_record(rec, win_rec.Event.MouseEvent);
case WINDOW_BUFFER_SIZE_EVENT:
// TODO: Handle window resizing
return false;
default:
record->type = ESCAPE;
rec->type = ESCAPE;
}
return true;
}
@ -134,14 +136,14 @@ bool WinBlockInput(struct RecordBuffer *buf)
pthread_mutex_lock(&buf->mutex);
for (size_t i = 0; i < count; i++) {
struct Record record;
record.timestamp = now;
struct InputRecord rec;
rec.timestamp = now;
bool include = dispatch_record(&record, win_buf[i]);
bool include = dispatch_record(&rec, win_buf[i]);
if (!include)
continue;
buf->records[buf->count++] = record;
buf->records[buf->count++] = rec;
}
pthread_mutex_unlock(&buf->mutex);

View file

@ -16,6 +16,15 @@
#include "win.h"
#endif
struct Instance {
struct Controller ctrl;
struct Terminal term;
struct Delegate on_start;
struct Delegate on_update;
struct Delegate on_draw;
};
const u8 I[16] = {
0, 0, 0, 0,
0, 0, 0, 0,
@ -58,16 +67,6 @@ const u8 L[9] = {
0, 0, 0
};
struct Instance {
struct Ctrl ctrl;
struct Delegate on_start;
struct Delegate on_update;
struct Delegate on_draw;
struct Terminal term;
};
struct CtrlBind {
enum CtrlCode code;
u16 bind;
@ -94,19 +93,18 @@ void *Update(void *args)
{
struct Instance *game = args;
struct TChar4 blks[game->term.area];
game->term.blks = blks;
while (true) {
// Input
CtrlPoll(&game->ctrl);
if (CtrlGet(&game->ctrl, LEFT, KEY)->button.is_down)
printf("left down this frame\n");
// Game logic
Invoke(&game->on_update, game);
//Invoke(&game->on_update, game);
// Draw
TermOut(&game->term);
puts(game->term.buf);
//TermOut(&game->term);
//puts(game->term.buf);
}
}
@ -129,21 +127,26 @@ bool Start(struct Instance *game)
if (!NewTerm(&game->term, 20, 20))
return false;
if (!NewDelegate(&game->on_start, 16))
return false;
if (!NewDelegate(&game->on_update, 16))
return false;
if (!NewDelegate(&game->on_draw, 16))
return false;
return true;
}
int main()
{
struct Instance game;
Start(&game);
if (!Start(&game))
exit(1);
#ifdef _WIN32
if(!WindowsInit(&game.term)) {
printf("FUCK");
if(!WindowsInit(&game.term))
exit(1);
}
#endif
printf("does it work");
StartInput(&game.ctrl);
Loop(&game);

View file

@ -35,9 +35,14 @@ size_t term_buf_size(size_t area, size_t hgt)
return reset_str_len + (max_color_str_len + 1) * area + hgt + 1;
}
size_t blks_size(size_t area)
struct TChar4 *alloc_blks(size_t area)
{
return area * sizeof(struct TChar4);
return calloc(area, sizeof(struct TChar4));
}
char *alloc_buf(size_t buf_size)
{
return malloc(buf_size);
}
bool NewTerm(struct Terminal *term, size_t wid, size_t hgt)
@ -45,17 +50,17 @@ bool NewTerm(struct Terminal *term, size_t wid, size_t hgt)
size_t area = wid * hgt;
size_t buf_size = term_buf_size(area, hgt);
struct TChar4 *tchs = malloc(blks_size(area));
char *buf = malloc(buf_size);
struct TChar4 *blks = alloc_blks(area);
char *buf = alloc_buf(buf_size);
if (tchs == nullptr or buf == nullptr)
if (blks == nullptr or buf == nullptr)
return false;
*term = (struct Terminal) {
.wid = wid,
.hgt = hgt,
.area = area,
.blks = tchs,
.blks = blks,
.buf_size = buf_size,
.buf = buf,
@ -70,8 +75,9 @@ bool ResizeTerm(struct Terminal *term, size_t wid, size_t hgt)
size_t area = wid * hgt;
size_t buf_size = term_buf_size(area, hgt);
struct TChar4 *tchs = realloc(term->blks, blks_size(area));
struct TChar4 *tchs = realloc(term->blks, area * sizeof(struct TChar4));
char *buf = realloc(term->buf, buf_size);
if (tchs == nullptr or buf == nullptr)
return false;

BIN
test.exe

Binary file not shown.