summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorVito Caputo <vcaputo@pengaru.com>2020-06-12 22:39:15 -0700
committerVito Caputo <vcaputo@pengaru.com>2020-06-12 22:39:15 -0700
commit55ce5773333b41229798c2a9b238812660707b7d (patch)
treeb11909013fe0320e09bde52807209f710a28bb33
parent19acc6de674d44d44f8d3bcb66568de3e5abfe3a (diff)
libstage: add return value to stage_render_func_tHEADmaster
This introduces some stage_render() flow control and render-time freeing of nodes via the nodes render_func(). It's particularly useful for one-shot ephemeral nodes which are thrown on-screen and require nothing more than their render and free funcs for a full lifecycle. An example would be something running an effect briefly which runs autonomously from just a timer alone, returning the free request from the final render once the ending time arrives.
-rw-r--r--src/stage.c28
-rw-r--r--src/stage.h8
2 files changed, 28 insertions, 8 deletions
diff --git a/src/stage.c b/src/stage.c
index a714f1f..63afbcb 100644
--- a/src/stage.c
+++ b/src/stage.c
@@ -302,19 +302,33 @@ static void _prepare_stage(stage_t *stage, float alpha, void *render_ctxt)
}
-static void _render_stage(const stage_t *stage, float alpha, void *render_ctxt)
+static void _render_stage(stage_t *stage, float alpha, void *render_ctxt)
{
- float a = alpha * stage->alpha;
+ stage_render_func_ret_t r = STAGE_RENDER_FUNC_RET_CONTINUE;
+ float a;
assert(stage);
+ a = alpha * stage->alpha;
+
if (stage->ops->render_func)
- stage->ops->render_func(stage, stage->object, a, render_ctxt);
+ r = stage->ops->render_func(stage, stage->object, a, render_ctxt);
+
+ switch (r) {
+ case STAGE_RENDER_FUNC_RET_FREE:
+ stage_free(stage);
+ case STAGE_RENDER_FUNC_RET_SKIP:
+ return;
+ case STAGE_RENDER_FUNC_RET_CONTINUE:
+ break;
+ default:
+ assert(0);
+ }
for (int i = 0; i < STAGE_LAYERS_MAX; i++) {
- stage_t *s;
+ stage_t *s, *_s;
- DLL_FOR_EACH_ENTRY(&stage->layers[i], s, stage_t, layer) {
+ DLL_FOR_EACH_ENTRY_SAFE(&stage->layers[i], s, _s, stage_t, layer) {
if (!s->active)
continue;
@@ -342,11 +356,11 @@ int stage_render(stage_t *stage, void *render_ctxt)
_prepare_stage(stage, 1.f, render_ctxt);
if (stage->dirty) {
+ stage->dirty = 0;
+
if (stage->active)
_render_stage(stage, 1.f, render_ctxt);
- stage->dirty = 0;
-
return 1;
}
diff --git a/src/stage.h b/src/stage.h
index 40f2057..b64e095 100644
--- a/src/stage.h
+++ b/src/stage.h
@@ -22,8 +22,14 @@
typedef struct stage_t stage_t;
+typedef enum stage_render_func_ret_t {
+ STAGE_RENDER_FUNC_RET_CONTINUE,
+ STAGE_RENDER_FUNC_RET_SKIP,
+ STAGE_RENDER_FUNC_RET_FREE
+} stage_render_func_ret_t;
+
typedef void (stage_prepare_func_t)(stage_t *stage, void *object, float alpha, void *render_ctxt);
-typedef void (stage_render_func_t)(const stage_t *stage, void *object, float alpha, void *render_ctxt);
+typedef stage_render_func_ret_t (stage_render_func_t)(const stage_t *stage, void *object, float alpha, void *render_ctxt);
typedef void (stage_free_func_t)(const stage_t *stage, void *object);
typedef struct stage_ops_t {
© 2020 All Rights Reserved