fixes, improve menu extending, comments
This commit is contained in:
@@ -5,7 +5,7 @@
|
||||
#include "liquid.h"
|
||||
#include "graphics/drawing.h"
|
||||
|
||||
#define BOOTANIM_TIME_MS 100
|
||||
#define BOOTANIM_TIME_MS 2000
|
||||
|
||||
struct BootScene {
|
||||
struct Scene base;
|
||||
|
||||
@@ -59,6 +59,11 @@ static void deinit(struct MenuScene *self)
|
||||
{
|
||||
free(self->items);
|
||||
self->items = NULL;
|
||||
|
||||
if (self->extra_deinit) {
|
||||
self->extra_deinit((struct Scene *) self);
|
||||
self->extra = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
struct MenuScene *NewScene_Menu(struct MenuItem *items, size_t items_len) {
|
||||
@@ -68,6 +73,10 @@ struct MenuScene *NewScene_Menu(struct MenuItem *items, size_t items_len) {
|
||||
scene->base.onInput = (Scene_onInput_t) onInput;
|
||||
scene->base.deinit = (Scene_deinit_t) deinit;
|
||||
|
||||
// onChildReturn is free to set by subclass
|
||||
|
||||
// TODO long selected label scrolling on tick
|
||||
|
||||
scene->items = items;
|
||||
scene->items_len = items_len;
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* TODO file description
|
||||
* Scrollable menu
|
||||
*
|
||||
* Created on 2020/01/05.
|
||||
*/
|
||||
@@ -12,13 +12,26 @@
|
||||
|
||||
#define MENUITEM_LABEL_LEN 30
|
||||
|
||||
/**
|
||||
* One item of the menu
|
||||
*/
|
||||
struct MenuItem {
|
||||
// menu label
|
||||
char label[MENUITEM_LABEL_LEN];
|
||||
// item tag (useful with dynamically generated menus)
|
||||
uint32_t tag;
|
||||
};
|
||||
|
||||
struct MenuScene;
|
||||
|
||||
/**
|
||||
* Selection handler.
|
||||
*
|
||||
* When an item is selected, this abstract method is fired to determine what should happen.
|
||||
*
|
||||
* The selected item is available as scene.selected.
|
||||
* Return SceneEvent to take, e.g. to close the menu, or to open a sub-scene.
|
||||
*/
|
||||
typedef struct SceneEvent (*MenuScene_onSelect_t)(struct MenuScene *scene);
|
||||
|
||||
struct MenuScene {
|
||||
@@ -33,10 +46,21 @@ struct MenuScene {
|
||||
int32_t selected;
|
||||
// selection handler
|
||||
MenuScene_onSelect_t onSelect;
|
||||
// Extra field for the instance's private use.
|
||||
void *private;
|
||||
// Extra field for the subclass's private use.
|
||||
void *extra;
|
||||
// fp for extra's deinit function
|
||||
Scene_deinit_t extra_deinit;
|
||||
};
|
||||
|
||||
/**
|
||||
* Create a new items menu.
|
||||
*
|
||||
* This is normally called from a subclass.
|
||||
*
|
||||
* @param items - menu items on heap (the MenuScene will free them on close)
|
||||
* @param items_len - item count
|
||||
* @return the menu
|
||||
*/
|
||||
struct MenuScene *NewScene_Menu(struct MenuItem *items, size_t items_len);
|
||||
|
||||
#endif //REFLOWER_SCENE_MENU_H
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
#include "scenes.h"
|
||||
#include "liquid.h"
|
||||
#include <malloc.h>
|
||||
#include <stdio.h>
|
||||
#include "graphics/nokia.h"
|
||||
#include "scenes.h"
|
||||
#include "liquid.h"
|
||||
#include "graphics/drawing.h"
|
||||
#include "scene_number.h"
|
||||
|
||||
|
||||
@@ -9,20 +9,27 @@
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
/**
|
||||
* Options passed to the NumberScene constructor
|
||||
*/
|
||||
struct NumberSceneOpts {
|
||||
// Screen title
|
||||
char label[15];
|
||||
// Unit added to the value
|
||||
char unit[8];
|
||||
// Initial value
|
||||
int32_t value;
|
||||
// min value
|
||||
int32_t min;
|
||||
// max value
|
||||
int32_t max;
|
||||
};
|
||||
|
||||
/**
|
||||
* Create number picker.
|
||||
*
|
||||
* The result is passed back as status.
|
||||
*
|
||||
* "opts" must be on heap and will be internally mutated.
|
||||
* The scene frees them on exit, returning the selected value as status.
|
||||
*
|
||||
* @param opts
|
||||
* @return
|
||||
|
||||
@@ -12,11 +12,10 @@
|
||||
|
||||
struct Priv {
|
||||
int32_t number;
|
||||
Scene_deinit_t parent_deinit;
|
||||
};
|
||||
|
||||
static struct SceneEvent onSelect(struct MenuScene *self) {
|
||||
struct Priv *priv = self->private;
|
||||
struct Priv *priv = self->extra;
|
||||
|
||||
if (self->selected == 0) {
|
||||
return SceneEvent_Close(0, NULL);
|
||||
@@ -46,19 +45,15 @@ static struct SceneEvent onSelect(struct MenuScene *self) {
|
||||
return SceneEvent_None();
|
||||
}
|
||||
|
||||
static void deinit(struct MenuScene *self)
|
||||
static void priv_deinit(struct MenuScene *self)
|
||||
{
|
||||
struct Priv *priv = self->private;
|
||||
if (priv->parent_deinit) {
|
||||
priv->parent_deinit((struct Scene *) self);
|
||||
}
|
||||
free(self->private);
|
||||
self->private = NULL;
|
||||
free(self->extra);
|
||||
self->extra = NULL;
|
||||
}
|
||||
|
||||
static struct SceneEvent onChildReturn(struct MenuScene *self, uint32_t tag, int32_t status, void *data)
|
||||
{
|
||||
struct Priv *priv = self->private;
|
||||
struct Priv *priv = self->extra;
|
||||
if (tag == 99) {
|
||||
priv->number = status;
|
||||
snprintf(self->items[2].label, MENUITEM_LABEL_LEN, "Set=%d°C", priv->number);
|
||||
@@ -88,10 +83,10 @@ struct Scene *NewScene_MenuTest() {
|
||||
// private data added by the subclass
|
||||
struct Priv *priv = calloc(1, sizeof(struct Priv));
|
||||
priv->number = 0;
|
||||
priv->parent_deinit = scene->base.deinit;
|
||||
scene->private = priv;
|
||||
scene->extra = priv;
|
||||
scene->extra_deinit = (Scene_deinit_t) priv_deinit;
|
||||
|
||||
scene->base.deinit = (Scene_deinit_t) deinit;
|
||||
// add a child return handler (base does not use this)
|
||||
scene->base.onChildReturn = (Scene_onChildReturn_t) onChildReturn;
|
||||
|
||||
return (struct Scene *) scene;
|
||||
|
||||
Reference in New Issue
Block a user