src/ascension/scene.h

Tue, 16 Apr 2024 22:20:17 +0200

author
Mike Becker <universe@uap-core.de>
date
Tue, 16 Apr 2024 22:20:17 +0200
changeset 63
e3cacdd636e4
parent 61
b7954818a6b7
permissions
-rw-r--r--

implement mouse motion and key press events

universe@21 1 /*
universe@21 2 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
universe@21 3 * Copyright 2023 Mike Becker. All rights reserved.
universe@21 4 *
universe@21 5 * Redistribution and use in source and binary forms, with or without
universe@21 6 * modification, are permitted provided that the following conditions are met:
universe@21 7 *
universe@21 8 * 1. Redistributions of source code must retain the above copyright
universe@21 9 * notice, this list of conditions and the following disclaimer.
universe@21 10 *
universe@21 11 * 2. Redistributions in binary form must reproduce the above copyright
universe@21 12 * notice, this list of conditions and the following disclaimer in the
universe@21 13 * documentation and/or other materials provided with the distribution.
universe@21 14 *
universe@21 15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
universe@21 16 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
universe@21 17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
universe@21 18 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
universe@21 19 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
universe@21 20 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
universe@21 21 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
universe@21 22 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
universe@21 23 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
universe@21 24 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
universe@21 25 * POSSIBILITY OF SUCH DAMAGE.
universe@21 26 */
universe@21 27
universe@21 28 #ifndef ASCENSION_SCENE_H
universe@21 29 #define ASCENSION_SCENE_H
universe@21 30
universe@37 31 #include "datatypes.h"
universe@32 32 #include "transform.h"
universe@37 33 #include "camera.h"
universe@37 34
universe@47 35 #include <cx/list.h>
universe@32 36
universe@29 37 typedef struct AscSceneNode AscSceneNode;
universe@29 38
universe@29 39 typedef void(*asc_scene_free_func)(AscSceneNode*);
universe@32 40 typedef void(*asc_scene_update_func)(AscSceneNode*);
universe@29 41 typedef void(*asc_scene_draw_func)(AscSceneNode const*);
universe@29 42
universe@37 43 enum AscRenderGroup {
universe@41 44 ASC_RENDER_GROUP_SPRITE_OPAQUE,
universe@47 45 ASC_RENDER_GROUP_SPRITE_BLEND,
universe@47 46 ASC_RENDER_GROUP_COUNT
universe@37 47 };
universe@37 48
universe@29 49 struct AscSceneNode {
universe@29 50 AscSceneNode *parent;
universe@29 51 AscSceneNode *prev;
universe@29 52 AscSceneNode *next;
universe@29 53 AscSceneNode *children;
universe@47 54 CxList *behaviors;
universe@29 55 asc_scene_free_func free_func;
universe@32 56 asc_scene_update_func update_func;
universe@29 57 asc_scene_draw_func draw_func;
universe@63 58 unsigned depth; // TODO: do we really need this bullshit?
universe@45 59 asc_vec3f position;
universe@45 60 asc_vec3f rotation;
universe@45 61 asc_vec3f scale;
universe@45 62 asc_transform transform;
universe@38 63 asc_transform world_transform;
universe@37 64 enum AscRenderGroup render_group;
universe@58 65 /**
universe@58 66 * Custom flags for this node.
universe@58 67 * The #ASC_SCENE_NODE_FLAGS_MASK bits are reserved for general flags.
universe@58 68 */
universe@58 69 uint32_t flags;
universe@29 70 };
universe@29 71
universe@61 72 #define ASC_SCENE_NODE_FLAGS_MASK 0xFF000000
universe@61 73 #define ASC_SCENE_NODE_UPDATE_GRAPHICS 0x01000000
universe@61 74 #define ASC_SCENE_NODE_UPDATE_TRANSFORM 0x02000000
universe@61 75 #define ASC_SCENE_NODE_HIDDEN 0x80000000
universe@58 76
universe@29 77 /**
universe@47 78 * Place this as first member of a structure that shall be used as a scene node.
universe@29 79 */
universe@32 80 #define extend_asc_scene_node AscSceneNode base
universe@29 81
universe@37 82 /**
universe@47 83 * Draws the scene with the specified root node.
universe@37 84 *
universe@47 85 * @param root the root node of the scene graph
universe@47 86 * @param viewport the window viewport the scene shall be drawn to
universe@47 87 * @param camera the camera to obtain the view and projection matrix from
universe@37 88 */
universe@29 89 __attribute__((__nonnull__))
universe@47 90 void asc_scene_draw(AscSceneNode *root, asc_recti viewport, AscCamera *camera);
universe@29 91
universe@29 92 /**
universe@29 93 * Creates an empty node that may serve as a container for other nodes.
universe@29 94 *
universe@29 95 * The free_func of this node will be a simple free().
universe@29 96 *
universe@29 97 * @return the new node
universe@29 98 */
universe@29 99 AscSceneNode *asc_scene_node_empty(void);
universe@21 100
universe@47 101 /**
universe@47 102 * Unlinks the node from its parent and frees the entire subtree.
universe@47 103 *
universe@47 104 * The free_func of this node and all child nodes is called, starting
universe@47 105 * with the leaf nodes and terminating with \p node.
universe@47 106 *
universe@47 107 * @param node the node to unlink
universe@47 108 */
universe@21 109 void asc_scene_node_free(AscSceneNode *node);
universe@21 110
universe@47 111 /**
universe@47 112 * Links a node to a (new) parent.
universe@47 113 *
universe@47 114 * @param parent the (new) parent
universe@47 115 * @param node the node to link
universe@47 116 */
universe@29 117 __attribute__((__nonnull__))
universe@33 118 void asc_scene_node_link(
universe@33 119 AscSceneNode *restrict parent,
universe@33 120 AscSceneNode *restrict node
universe@33 121 );
universe@21 122
universe@47 123 /**
universe@47 124 * Unlinks a node from its parent.
universe@47 125 *
universe@47 126 * This might be useful to temporarily remove a subtree from a scene.
universe@47 127 * To permanently remove the node use asc_scene_node_free().
universe@47 128 *
universe@47 129 * @param node the node to unlink
universe@47 130 */
universe@29 131 __attribute__((__nonnull__))
universe@21 132 void asc_scene_node_unlink(AscSceneNode *node);
universe@21 133
universe@47 134 /**
universe@47 135 * Adds a behavior function to the node.
universe@47 136 *
universe@47 137 * A behavior function MUST NOT be added more than once to the same node.
universe@47 138 * This will not be checked.
universe@47 139 *
universe@47 140 * @param node the node
universe@47 141 * @param behavior the behavior function
universe@47 142 */
universe@33 143 __attribute__((__nonnull__))
universe@47 144 void asc_scene_add_behavior(
universe@33 145 AscSceneNode *node,
universe@33 146 asc_scene_update_func behavior
universe@33 147 );
universe@33 148
universe@47 149 /**
universe@47 150 * Removes a behavior function from the node.
universe@47 151 *
universe@47 152 * If the behavior function is not attached to this node, this function
universe@47 153 * does nothing.
universe@47 154 *
universe@47 155 * @param node the node
universe@47 156 * @param behavior the behavior function
universe@47 157 */
universe@33 158 __attribute__((__nonnull__))
universe@47 159 void asc_scene_remove_behavior(
universe@47 160 AscSceneNode *node,
universe@47 161 asc_scene_update_func behavior
universe@47 162 );
universe@33 163
universe@61 164 __attribute__((__nonnull__))
universe@61 165 void asc_node_update(AscSceneNode *node);
universe@45 166
universe@38 167 __attribute__((__nonnull__))
universe@61 168 void asc_node_update_transform(AscSceneNode *node);
universe@45 169
universe@45 170
universe@45 171 __attribute__((__nonnull__)) static inline
universe@45 172 void asc_set_position(AscSceneNode *node, float x, float y, float z) {
universe@45 173 node->position.x = x;
universe@45 174 node->position.y = y;
universe@45 175 node->position.z = z;
universe@61 176 asc_node_update_transform(node);
universe@45 177 }
universe@45 178
universe@45 179 __attribute__((__nonnull__)) static inline
universe@45 180 void asc_set_position2d(AscSceneNode *node, int x, int y) {
universe@45 181 node->position.x = (float)x;
universe@45 182 node->position.y = (float)y;
universe@45 183 node->position.z = 0.f;
universe@61 184 asc_node_update_transform(node);
universe@45 185 }
universe@45 186
universe@45 187 __attribute__((__nonnull__)) static inline
universe@45 188 asc_vec2i asc_get_position2d(AscSceneNode *node) {
universe@45 189 return (asc_vec2i) {(int) node->position.x, (int) node->position.y};
universe@45 190 }
universe@45 191
universe@45 192 __attribute__((__nonnull__)) static inline
universe@45 193 void asc_set_scale(AscSceneNode *node, float width, float height, float depth) {
universe@45 194 node->scale.width = width;
universe@45 195 node->scale.height = height;
universe@45 196 node->scale.depth = depth;
universe@61 197 asc_node_update_transform(node);
universe@45 198 }
universe@45 199
universe@45 200 __attribute__((__nonnull__)) static inline
universe@45 201 void asc_set_scale2d(AscSceneNode *node, int width, int height) {
universe@45 202 node->scale.width = (float)width;
universe@45 203 node->scale.height = (float)height;
universe@45 204 node->scale.depth = 1.f;
universe@61 205 asc_node_update_transform(node);
universe@45 206 }
universe@45 207
universe@45 208 __attribute__((__nonnull__)) static inline
universe@45 209 asc_vec2i asc_get_scale2d(AscSceneNode *node) {
universe@45 210 return (asc_vec2i) {(int) node->scale.width, (int) node->scale.height};
universe@45 211 }
universe@38 212
universe@21 213 #endif // ASCENSION_SCENE_H
universe@21 214

mercurial