Checkboxes

This commit is contained in:
Scott Duensing 2022-06-29 19:29:21 -05:00
parent 33fd278e1d
commit b5eec0431d
5 changed files with 206 additions and 8 deletions

View file

@ -53,6 +53,7 @@ HEADERS += \
src/gui/image.h \
src/gui/surface.h \
src/gui/widgets/button.h \
src/gui/widgets/checkbox.h \
src/gui/widgets/label.h \
src/gui/widgets/picture.h \
src/gui/wmwindow.h \
@ -71,6 +72,7 @@ SOURCES += \
src/gui/image.c \
src/gui/surface.c \
src/gui/widgets/button.c \
src/gui/widgets/checkbox.c \
src/gui/widgets/label.c \
src/gui/widgets/picture.c \
src/gui/wmwindow.c \

View file

@ -30,6 +30,7 @@
#include "wmwindow.h"
#include "widgets/button.h"
#include "widgets/checkbox.h"
#include "widgets/label.h"
#include "widgets/picture.h"
@ -195,10 +196,10 @@ uint8_t guiStartup(int16_t width, int16_t height, int16_t depth) {
// Register standard widgets.
guiRegister(windowRegister);
guiRegister(labelRegister);
guiRegister(pictureRegister);
guiRegister(labelRegister); // Above other widgets in list since many depend on Label.
guiRegister(buttonRegister);
guiRegister(checkboxRegister);
guiRegister(pictureRegister);
return SUCCESS;
}

View file

@ -0,0 +1,138 @@
/*
* Roo/E, the Kangaroo Punch Portable GUI Toolkit
* Copyright (C) 2022 Scott Duensing
*
* http://kangaroopunch.com
*
*
* This file is part of Roo/E.
*
* Roo/E is free software: you can redistribute it and/or modify it under the
* terms of the GNU Affero General Public License as published by the Free
* Software Foundation, either version 3 of the License, or (at your option)
* any later version.
*
* Roo/E is distributed in the hope that it will be useful, but WITHOUT ANY
* WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
* details.
*
* You should have received a copy of the GNU Affero General Public License
* along with Roo/E. If not, see <https://www.gnu.org/licenses/>.
*
*/
#include "../wmwindow.h"
#include "checkbox.h"
uint8_t __MAGIC_CHECKBOX = 0;
static void checkboxClick(WidgetT *widget, uint16_t x, uint16_t y, uint8_t event, void *data);
static void checkboxDestroy(struct WidgetS *widget, ...);
static void checkboxPaint(struct WidgetS *widget, ...);
static void checkboxClick(WidgetT *widget, uint16_t x, uint16_t y, uint8_t event, void *data) {
CheckboxT *c = (CheckboxT *)widget;
if (event == CLICK_LEFT_UP) {
// Toggle value.
c->value = !c->value;
// Call the actual click event if it exists.
if (c->handler) c->handler(widget, x, y, event, data);
// Repaint.
guiWidgetDirtySet(widget, 1);
}
}
void checkboxClickSet(CheckboxT *checkbox, ClickHandlerT handler, void *data) {
checkbox->handler = handler;
checkbox->base.data = data;
}
CheckboxT *checkboxCreate(char *label, uint8_t value, ...) {
CheckboxT *c = NULL;
uint16_t width;
uint16_t height;
FontT *f = __guiFontVGA8x16;
NEW(CheckboxT, c);
memset(c, 0, sizeof(CheckboxT));
c->value = value;
c->label = labelCreate(LABEL_ALIGN_LEFT, f, label);
if (!c->label) {
DEL(c);
return NULL;
}
// Checkbox is (height - 3) square. We skip two pixels on the bottom and one on the top to look okay with decender characters.
height = fontHeightGet(f);
width = fontWidthCharactersGet(label) * fontWidthGet(f) + (height * 3);
guiWidgetBaseSet(W(c), __MAGIC_CHECKBOX, width, height);
return c;
}
static void checkboxDestroy(struct WidgetS *widget, ...) {
CheckboxT *c = (CheckboxT *)widget;
guiWidgetDestroy(W(c->label));
DEL(c);
}
static void checkboxPaint(struct WidgetS *widget, ...) {
CheckboxT *c = (CheckboxT *)widget;
int16_t w;
int16_t h;
if (guiWidgetDirtyGet(widget)) {
guiWidgetDirtySet(widget, 0);
h = fontHeightGet(c->label->font) - 2;
w = h * 1.5;
// Paint checkbox.
surfaceBoxHighlight(c->base.r.x, c->base.r.y + 1, c->base.r.x + h, c->base.r.y + h, GUI_BLACK, GUI_WHITE);
surfaceBoxFilled(c->base.r.x + 1, c->base.r.y + 2, c->base.r.x + h - 1, c->base.r.y + h - 1, c->value ? GUI_DARKGRAY : GUI_WHITE);
// Paint label.
guiWidgetPaintManually(W(c->label), c->base.r.x + w, c->base.r.y);
}
}
RegisterT *checkboxRegister(uint8_t magic) {
static RegisterT reg = {
"Checkbox",
checkboxClick,
checkboxDestroy,
checkboxPaint,
NULL // No unregister handler.
};
// One-time widget startup code.
__MAGIC_CHECKBOX = magic;
return &reg;
}
uint8_t checkboxValueGet(CheckboxT *checkbox) {
return checkbox->value;
}
void checkboxValueSet(CheckboxT *checkbox, uint8_t value) {
checkbox->value = (value != 0);
// Repaint.
guiWidgetDirtySet(W(checkbox), 1);
}

View file

@ -0,0 +1,52 @@
/*
* Roo/E, the Kangaroo Punch Portable GUI Toolkit
* Copyright (C) 2022 Scott Duensing
*
* http://kangaroopunch.com
*
*
* This file is part of Roo/E.
*
* Roo/E is free software: you can redistribute it and/or modify it under the
* terms of the GNU Affero General Public License as published by the Free
* Software Foundation, either version 3 of the License, or (at your option)
* any later version.
*
* Roo/E is distributed in the hope that it will be useful, but WITHOUT ANY
* WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
* details.
*
* You should have received a copy of the GNU Affero General Public License
* along with Roo/E. If not, see <https://www.gnu.org/licenses/>.
*
*/
#ifndef CHECKBOX_H
#define CHECKBOX_H
#include "../gui.h"
#include "label.h"
typedef struct CheckboxS {
WidgetT base; // Required by all widgets.
LabelT *label; // Label to display text.
ClickHandlerT handler; // Actual event handler.
uint8_t value; // Is the button being pressed?
} CheckboxT;
extern uint8_t __MAGIC_CHECKBOX; // Magic ID assigned to us from the GUI.
void checkboxClickSet(CheckboxT *checkbox, ClickHandlerT handler, void *data);
CheckboxT *checkboxCreate(char *label, uint8_t value, ...);
RegisterT *checkboxRegister(uint8_t magic);
uint8_t checkboxValueGet(CheckboxT *checkbox);
void checkboxValueSet(CheckboxT *checkbox, uint8_t value);
#endif // CHECKBOX_H

View file

@ -28,6 +28,7 @@
#include "gui/widgets/label.h"
#include "gui/widgets/picture.h"
#include "gui/widgets/button.h"
#include "gui/widgets/checkbox.h"
void clickHandler(WidgetT *widget, uint16_t x, uint16_t y, uint8_t event, void *data) {
@ -37,11 +38,12 @@ void clickHandler(WidgetT *widget, uint16_t x, uint16_t y, uint8_t event, void *
int main(int argc, char *argv[]) {
char title[256];
uint16_t i;
LabelT *l = NULL;
ButtonT *b = NULL;
WindowT *w = NULL;
char title[256];
uint16_t i;
LabelT *l = NULL;
ButtonT *b = NULL;
CheckboxT *c = NULL;
WindowT *w = NULL;
(void)argc;
@ -61,6 +63,9 @@ int main(int argc, char *argv[]) {
b = buttonCreate("Button", clickHandler, NULL);
windowWidgetAdd(w, 20, 40, W(b));
c = checkboxCreate("Checkbox", 0);
windowWidgetAdd(w, 20, 80, W(c));
}
guiRun();
guiShutdown();