[Add] Basic toolkit focus. We can now completely navigate the menus etc with the keyboard.
This commit is contained in:
parent
521f3baa9f
commit
b1d1142739
12
src/menu.c
12
src/menu.c
@ -42,15 +42,17 @@ void menu_small(void) {
|
|||||||
|
|
||||||
wid = window_create("Menu", -1, -1, MENU_WIDTH, MENU_HEIGHT);
|
wid = window_create("Menu", -1, -1, MENU_WIDTH, MENU_HEIGHT);
|
||||||
|
|
||||||
window_addButton(wid, 20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
|
|
||||||
"btnExit", "Exit", (void(*)(char*))exit_game);
|
|
||||||
window_addButton(wid, 20, 20 + BUTTON_HEIGHT + 20,
|
|
||||||
BUTTON_WIDTH, BUTTON_HEIGHT,
|
|
||||||
"btnOptions", "Options", (void(*)(char*))edit_options);
|
|
||||||
window_addButton(wid, 20, 20 + BUTTON_HEIGHT*2 + 20*2,
|
window_addButton(wid, 20, 20 + BUTTON_HEIGHT*2 + 20*2,
|
||||||
BUTTON_WIDTH, BUTTON_HEIGHT,
|
BUTTON_WIDTH, BUTTON_HEIGHT,
|
||||||
"btnResume", "Resume", menu_small_close);
|
"btnResume", "Resume", menu_small_close);
|
||||||
|
|
||||||
|
window_addButton(wid, 20, 20, BUTTON_WIDTH, BUTTON_HEIGHT,
|
||||||
|
"btnExit", "Exit", (void(*)(char*))exit_game);
|
||||||
|
|
||||||
|
window_addButton(wid, 20, 20 + BUTTON_HEIGHT + 20,
|
||||||
|
BUTTON_WIDTH, BUTTON_HEIGHT,
|
||||||
|
"btnOptions", "Options", (void(*)(char*))edit_options);
|
||||||
|
|
||||||
menu_Open(MENU_SMALL);
|
menu_Open(MENU_SMALL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -14,8 +14,7 @@ typedef enum WidgetType_ {
|
|||||||
typedef enum WidgetStatus_ {
|
typedef enum WidgetStatus_ {
|
||||||
WIDGET_STATUS_NORMAL,
|
WIDGET_STATUS_NORMAL,
|
||||||
WIDGET_STATUS_MOUSEOVER,
|
WIDGET_STATUS_MOUSEOVER,
|
||||||
WIDGET_STATUS_MOUSEDOWN,
|
WIDGET_STATUS_MOUSEDOWN
|
||||||
WIDGET_STATUS_FOCUS
|
|
||||||
} WidgetStatus;
|
} WidgetStatus;
|
||||||
|
|
||||||
typedef struct Widget_ {
|
typedef struct Widget_ {
|
||||||
@ -57,6 +56,9 @@ typedef struct Window_ {
|
|||||||
unsigned int id; // Unique identifier.
|
unsigned int id; // Unique identifier.
|
||||||
char* name;
|
char* name;
|
||||||
|
|
||||||
|
int hidden; // Is it hidden?
|
||||||
|
int focus; // Which window is focused.
|
||||||
|
|
||||||
double x,y; // Position.
|
double x,y; // Position.
|
||||||
double w,h; // Dimensions.
|
double w,h; // Dimensions.
|
||||||
|
|
||||||
@ -79,6 +81,9 @@ static Window* window_wget(const unsigned int wid);
|
|||||||
static Widget* window_getwgt(const unsigned int wid, char* name);
|
static Widget* window_getwgt(const unsigned int wid, char* name);
|
||||||
// Input.
|
// Input.
|
||||||
static void toolkit_mouseEvent(SDL_Event* event);
|
static void toolkit_mouseEvent(SDL_Event* event);
|
||||||
|
static int toolkit_keyEvent(SDL_Event* event);
|
||||||
|
static void toolkit_nextFocus(void);
|
||||||
|
static void toolkit_triggerFocus(void);
|
||||||
// Render.
|
// Render.
|
||||||
static void window_render(Window* w);
|
static void window_render(Window* w);
|
||||||
static void toolkit_renderButton(Widget* btn, double bx, double by);
|
static void toolkit_renderButton(Widget* btn, double bx, double by);
|
||||||
@ -105,6 +110,9 @@ void window_addButton(const unsigned int wid, const int x, const int y, const in
|
|||||||
if(y < 0) wgt->y = wdw->h - wgt->h + y;
|
if(y < 0) wgt->y = wdw->h - wgt->h + y;
|
||||||
else wgt->y = (double)y;
|
else wgt->y = (double)y;
|
||||||
wgt->dat.btn.fptr = call;
|
wgt->dat.btn.fptr = call;
|
||||||
|
|
||||||
|
if(wdw->focus == -1) // Init the focus.
|
||||||
|
toolkit_nextFocus();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Add text to the window.
|
// Add text to the window.
|
||||||
@ -243,6 +251,9 @@ unsigned int window_create(char* name, const int x, const int y, const int w, co
|
|||||||
windows[nwindows].id = wid;
|
windows[nwindows].id = wid;
|
||||||
windows[nwindows].name = strdup(name);
|
windows[nwindows].name = strdup(name);
|
||||||
|
|
||||||
|
windows[nwindows].hidden = 0;
|
||||||
|
windows[nwindows].focus = -1;
|
||||||
|
|
||||||
windows[nwindows].w = (double) w;
|
windows[nwindows].w = (double) w;
|
||||||
windows[nwindows].h = (double) h;
|
windows[nwindows].h = (double) h;
|
||||||
if((x == -1) && (y == -1)) {
|
if((x == -1) && (y == -1)) {
|
||||||
@ -334,7 +345,7 @@ void window_destroyWidget(unsigned int wid, const char* wgtname) {
|
|||||||
// Render a window.
|
// Render a window.
|
||||||
static void window_render(Window* w) {
|
static void window_render(Window* w) {
|
||||||
int i;
|
int i;
|
||||||
double x, y;
|
double x, y, wid, hei;
|
||||||
glColour *lc, *c, *dc, *oc;
|
glColour *lc, *c, *dc, *oc;
|
||||||
|
|
||||||
// Position.
|
// Position.
|
||||||
@ -520,6 +531,30 @@ static void window_render(Window* w) {
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// Focus widget.
|
||||||
|
if(w->focus != -1) {
|
||||||
|
x += w->widgets[w->focus].x;
|
||||||
|
y += w->widgets[w->focus].y;
|
||||||
|
wid = w->widgets[w->focus].w;
|
||||||
|
hei = w->widgets[w->focus].h;
|
||||||
|
|
||||||
|
glBegin(GL_LINE_LOOP);
|
||||||
|
COLOUR(cBlack);
|
||||||
|
// Left.
|
||||||
|
glVertex2d(x-3., y);
|
||||||
|
glVertex2d(x-3., y+hei);
|
||||||
|
// Top.
|
||||||
|
glVertex2d(x, y+hei+3.);
|
||||||
|
glVertex2d(x+wid, y+hei+3.);
|
||||||
|
// Right.
|
||||||
|
glVertex2d(x+wid+3., y+hei);
|
||||||
|
glVertex2d(x+wid+3., y);
|
||||||
|
// Bottom.
|
||||||
|
glVertex2d(x+wid, y-3.);
|
||||||
|
glVertex2d(x, y-3.);
|
||||||
|
glVertex2d(x-3., y);
|
||||||
|
glEnd();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Renders a button.
|
// Renders a button.
|
||||||
@ -702,6 +737,9 @@ int toolkit_input(SDL_Event* event) {
|
|||||||
case SDL_MOUSEBUTTONUP:
|
case SDL_MOUSEBUTTONUP:
|
||||||
toolkit_mouseEvent(event);
|
toolkit_mouseEvent(event);
|
||||||
return 1; // Block input.
|
return 1; // Block input.
|
||||||
|
case SDL_KEYDOWN:
|
||||||
|
case SDL_KEYUP:
|
||||||
|
return toolkit_keyEvent(event);
|
||||||
}
|
}
|
||||||
return 0; // Don't block unput.
|
return 0; // Don't block unput.
|
||||||
}
|
}
|
||||||
@ -767,6 +805,56 @@ static void toolkit_mouseEvent(SDL_Event* event) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Handle the key events.
|
||||||
|
static int toolkit_keyEvent(SDL_Event* event) {
|
||||||
|
SDLKey key = event->key.keysym.sym;
|
||||||
|
switch(key) {
|
||||||
|
case SDLK_TAB:
|
||||||
|
if(event->type == SDL_KEYDOWN)
|
||||||
|
toolkit_nextFocus();
|
||||||
|
return 1;
|
||||||
|
case SDLK_RETURN:
|
||||||
|
if(event->type == SDL_KEYDOWN)
|
||||||
|
toolkit_triggerFocus();
|
||||||
|
return 1;
|
||||||
|
default:
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Focus next widget.
|
||||||
|
static void toolkit_nextFocus(void) {
|
||||||
|
Window* wdw = &windows[nwindows-1]; // Get active window.
|
||||||
|
|
||||||
|
if(wdw->nwidgets==0)
|
||||||
|
wdw->focus = -1;
|
||||||
|
else if(wdw->focus >= wdw->nwidgets)
|
||||||
|
wdw->focus = -1;
|
||||||
|
else if((++wdw->focus+1) && // Just increment.
|
||||||
|
(wdw->widgets[wdw->focus].type == WIDGET_BUTTON))
|
||||||
|
return;
|
||||||
|
else
|
||||||
|
toolkit_nextFocus();
|
||||||
|
}
|
||||||
|
|
||||||
|
static void toolkit_triggerFocus(void) {
|
||||||
|
Window* wdw;
|
||||||
|
Widget* wgt;
|
||||||
|
|
||||||
|
wdw = &windows[nwindows-1];
|
||||||
|
|
||||||
|
if(wdw->focus == -1) return;
|
||||||
|
|
||||||
|
wgt = &wdw->widgets[wdw->focus];
|
||||||
|
|
||||||
|
switch(wgt->type) {
|
||||||
|
case WIDGET_BUTTON:
|
||||||
|
(*wgt->dat.btn.fptr)(wgt->name);
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Init.
|
// Init.
|
||||||
int toolkit_init(void) {
|
int toolkit_init(void) {
|
||||||
windows = malloc(sizeof(Window)*MIN_WINDOWS);
|
windows = malloc(sizeof(Window)*MIN_WINDOWS);
|
||||||
|
Loading…
Reference in New Issue
Block a user