You've already forked Microtransactions64
mirror of
https://github.com/Print-and-Panic/Microtransactions64.git
synced 2026-01-21 10:17:19 -08:00
Remove GRAPH_NODE_TYPE_FUNCTIONAL define & restore functionality using an alternative method. (#557)
Fixes Mirror Mario and similar things.
This commit is contained in:
@@ -123,11 +123,6 @@
|
||||
*/
|
||||
// #define FIX_REFLECT_MTX
|
||||
|
||||
/**
|
||||
* This improves performance a bit, and does not seem to break anything.
|
||||
*/
|
||||
#define DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
|
||||
/**
|
||||
* Disables all object shadows. You'll probably only want this either as a last resort for performance or if you're making a super stylized hack.
|
||||
*/
|
||||
|
||||
@@ -603,7 +603,6 @@ struct GraphNode *geo_make_first_child(struct GraphNode *newFirstChild) {
|
||||
return parent;
|
||||
}
|
||||
|
||||
#ifndef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
/**
|
||||
* Helper function for geo_call_global_function_nodes that recursively
|
||||
* traverses the scene graph and calls the functions of global nodes.
|
||||
@@ -612,11 +611,19 @@ void geo_call_global_function_nodes_helper(struct GraphNode *graphNode, s32 call
|
||||
struct GraphNode **globalPtr;
|
||||
struct GraphNode *curNode = graphNode;
|
||||
struct FnGraphNode *asFnNode;
|
||||
s16 type;
|
||||
|
||||
do {
|
||||
asFnNode = (struct FnGraphNode *) curNode;
|
||||
|
||||
if (curNode->type & GRAPH_NODE_TYPE_FUNCTIONAL) {
|
||||
type = curNode->type;
|
||||
|
||||
// Whether the type's corresponding struct has a FnGraphNode fnNode struct.
|
||||
if (type == GRAPH_NODE_TYPE_PERSPECTIVE
|
||||
|| type == GRAPH_NODE_TYPE_SWITCH_CASE
|
||||
|| type == GRAPH_NODE_TYPE_CAMERA
|
||||
|| type == GRAPH_NODE_TYPE_GENERATED_LIST
|
||||
|| type == GRAPH_NODE_TYPE_BACKGROUND
|
||||
|| type == GRAPH_NODE_TYPE_HELD_OBJ) {
|
||||
if (asFnNode->func != NULL) {
|
||||
asFnNode->func(callContext, curNode, NULL);
|
||||
}
|
||||
@@ -669,10 +676,9 @@ void geo_call_global_function_nodes(struct GraphNode *graphNode, s32 callContext
|
||||
geo_call_global_function_nodes_helper(graphNode->children, callContext);
|
||||
}
|
||||
|
||||
gCurGraphNodeRoot = 0;
|
||||
gCurGraphNodeRoot = NULL;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* When objects are cleared, this is called on all object nodes (loaded or unloaded).
|
||||
|
||||
@@ -50,7 +50,6 @@ enum GraphRenderFlags {
|
||||
#define GET_GRAPH_NODE_LAYER(flags) ((flags & GRAPH_RENDER_LAYERS_MASK) >> GRAPH_RENDER_FLAGS_SIZE)
|
||||
#endif
|
||||
|
||||
#ifdef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
// The discriminant for different types of geo nodes
|
||||
enum GraphNodeTypes {
|
||||
GRAPH_NODE_TYPE_ORTHO_PROJECTION,
|
||||
@@ -76,38 +75,6 @@ enum GraphNodeTypes {
|
||||
GRAPH_NODE_TYPE_ROOT,
|
||||
GRAPH_NODE_TYPE_START,
|
||||
};
|
||||
#else
|
||||
// Whether the node type has a function pointer of type GraphNodeFunc
|
||||
#define GRAPH_NODE_TYPE_FUNCTIONAL (1 << 8)
|
||||
|
||||
// The discriminant for different types of geo nodes
|
||||
enum GraphNodeTypes {
|
||||
GRAPH_NODE_TYPE_ROOT = 0x01,
|
||||
GRAPH_NODE_TYPE_ORTHO_PROJECTION = 0x02,
|
||||
GRAPH_NODE_TYPE_PERSPECTIVE = (0x03 | GRAPH_NODE_TYPE_FUNCTIONAL),
|
||||
GRAPH_NODE_TYPE_MASTER_LIST = 0x04,
|
||||
GRAPH_NODE_TYPE_START = 0x0A,
|
||||
GRAPH_NODE_TYPE_LEVEL_OF_DETAIL = 0x0B,
|
||||
GRAPH_NODE_TYPE_SWITCH_CASE = (0x0C | GRAPH_NODE_TYPE_FUNCTIONAL),
|
||||
GRAPH_NODE_TYPE_CAMERA = (0x14 | GRAPH_NODE_TYPE_FUNCTIONAL),
|
||||
GRAPH_NODE_TYPE_TRANSLATION_ROTATION = 0x15,
|
||||
GRAPH_NODE_TYPE_TRANSLATION = 0x16,
|
||||
GRAPH_NODE_TYPE_ROTATION = 0x17,
|
||||
GRAPH_NODE_TYPE_OBJECT = 0x18,
|
||||
GRAPH_NODE_TYPE_ANIMATED_PART = 0x19,
|
||||
GRAPH_NODE_TYPE_BILLBOARD = 0x1A,
|
||||
GRAPH_NODE_TYPE_DISPLAY_LIST = 0x1B,
|
||||
GRAPH_NODE_TYPE_SCALE = 0x1C,
|
||||
GRAPH_NODE_TYPE_SHADOW = 0x28,
|
||||
GRAPH_NODE_TYPE_OBJECT_PARENT = 0x29,
|
||||
GRAPH_NODE_TYPE_GENERATED_LIST = (0x2A | GRAPH_NODE_TYPE_FUNCTIONAL),
|
||||
GRAPH_NODE_TYPE_BACKGROUND = (0x2C | GRAPH_NODE_TYPE_FUNCTIONAL),
|
||||
GRAPH_NODE_TYPE_HELD_OBJ = (0x2E | GRAPH_NODE_TYPE_FUNCTIONAL),
|
||||
GRAPH_NODE_TYPE_CULLING_RADIUS = 0x2F,
|
||||
|
||||
GRAPH_NODE_TYPES_MASK = 0xFF,
|
||||
};
|
||||
#endif
|
||||
|
||||
// Passed as first argument to a GraphNodeFunc to give information about in
|
||||
// which context it was called and what it is expected to do.
|
||||
@@ -426,10 +393,8 @@ struct GraphNodeHeldObject *init_graph_node_held_object (struct
|
||||
struct GraphNode *geo_add_child (struct GraphNode *parent, struct GraphNode *childNode);
|
||||
struct GraphNode *geo_remove_child (struct GraphNode *graphNode);
|
||||
struct GraphNode *geo_make_first_child(struct GraphNode *newFirstChild);
|
||||
#ifndef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
void geo_call_global_function_nodes_helper(struct GraphNode *graphNode, s32 callContext);
|
||||
void geo_call_global_function_nodes (struct GraphNode *graphNode, s32 callContext);
|
||||
#endif
|
||||
void geo_reset_object_node(struct GraphNodeObject *graphNode);
|
||||
void geo_obj_init(struct GraphNodeObject *graphNode, void *sharedChild, Vec3f pos, Vec3s angle);
|
||||
void geo_obj_init_spawninfo(struct GraphNodeObject *graphNode, struct SpawnInfo *spawn);
|
||||
|
||||
@@ -212,18 +212,14 @@ void clear_area_graph_nodes(void) {
|
||||
s32 i;
|
||||
|
||||
if (gCurrentArea != NULL) {
|
||||
#ifndef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
geo_call_global_function_nodes(&gCurrentArea->graphNode->node, GEO_CONTEXT_AREA_UNLOAD);
|
||||
#endif
|
||||
gCurrentArea = NULL;
|
||||
gWarpTransition.isActive = FALSE;
|
||||
}
|
||||
|
||||
for (i = 0; i < AREA_COUNT; i++) {
|
||||
if (gAreaData[i].graphNode != NULL) {
|
||||
#ifndef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
geo_call_global_function_nodes(&gAreaData[i].graphNode->node, GEO_CONTEXT_AREA_INIT);
|
||||
#endif
|
||||
gAreaData[i].graphNode = NULL;
|
||||
}
|
||||
}
|
||||
@@ -248,18 +244,14 @@ void load_area(s32 index) {
|
||||
}
|
||||
|
||||
load_obj_warp_nodes();
|
||||
#ifndef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
geo_call_global_function_nodes(&gCurrentArea->graphNode->node, GEO_CONTEXT_AREA_LOAD);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
void unload_area(void) {
|
||||
if (gCurrentArea != NULL) {
|
||||
unload_objects_from_area(0, gCurrentArea->index);
|
||||
#ifndef DISABLE_GRAPH_NODE_TYPE_FUNCTIONAL
|
||||
geo_call_global_function_nodes(&gCurrentArea->graphNode->node, GEO_CONTEXT_AREA_UNLOAD);
|
||||
#endif
|
||||
|
||||
gCurrentArea->flags = AREA_FLAG_UNLOAD;
|
||||
gCurrentArea = NULL;
|
||||
|
||||
@@ -1262,6 +1262,34 @@ void geo_try_process_children(struct GraphNode *node) {
|
||||
}
|
||||
}
|
||||
|
||||
typedef void (*GeoProcessFunc)();
|
||||
|
||||
// See enum 'GraphNodeTypes' in 'graph_node.h'.
|
||||
static GeoProcessFunc GeoProcessJumpTable[] = {
|
||||
[GRAPH_NODE_TYPE_ORTHO_PROJECTION ] = geo_process_ortho_projection,
|
||||
[GRAPH_NODE_TYPE_PERSPECTIVE ] = geo_process_perspective,
|
||||
[GRAPH_NODE_TYPE_MASTER_LIST ] = geo_process_master_list,
|
||||
[GRAPH_NODE_TYPE_LEVEL_OF_DETAIL ] = geo_process_level_of_detail,
|
||||
[GRAPH_NODE_TYPE_SWITCH_CASE ] = geo_process_switch,
|
||||
[GRAPH_NODE_TYPE_CAMERA ] = geo_process_camera,
|
||||
[GRAPH_NODE_TYPE_TRANSLATION_ROTATION] = geo_process_translation_rotation,
|
||||
[GRAPH_NODE_TYPE_TRANSLATION ] = geo_process_translation,
|
||||
[GRAPH_NODE_TYPE_ROTATION ] = geo_process_rotation,
|
||||
[GRAPH_NODE_TYPE_OBJECT ] = geo_process_object,
|
||||
[GRAPH_NODE_TYPE_ANIMATED_PART ] = geo_process_animated_part,
|
||||
[GRAPH_NODE_TYPE_BILLBOARD ] = geo_process_billboard,
|
||||
[GRAPH_NODE_TYPE_DISPLAY_LIST ] = geo_process_display_list,
|
||||
[GRAPH_NODE_TYPE_SCALE ] = geo_process_scale,
|
||||
[GRAPH_NODE_TYPE_SHADOW ] = geo_process_shadow,
|
||||
[GRAPH_NODE_TYPE_OBJECT_PARENT ] = geo_process_object_parent,
|
||||
[GRAPH_NODE_TYPE_GENERATED_LIST ] = geo_process_generated_list,
|
||||
[GRAPH_NODE_TYPE_BACKGROUND ] = geo_process_background,
|
||||
[GRAPH_NODE_TYPE_HELD_OBJ ] = geo_process_held_object,
|
||||
[GRAPH_NODE_TYPE_CULLING_RADIUS ] = geo_try_process_children,
|
||||
[GRAPH_NODE_TYPE_ROOT ] = geo_try_process_children,
|
||||
[GRAPH_NODE_TYPE_START ] = geo_try_process_children,
|
||||
};
|
||||
|
||||
/**
|
||||
* Process a generic geo node and its siblings.
|
||||
* The first argument is the start node, and all its siblings will
|
||||
@@ -1283,28 +1311,7 @@ void geo_process_node_and_siblings(struct GraphNode *firstNode) {
|
||||
if (curGraphNode->flags & GRAPH_RENDER_CHILDREN_FIRST) {
|
||||
geo_try_process_children(curGraphNode);
|
||||
} else {
|
||||
switch (curGraphNode->type) {
|
||||
case GRAPH_NODE_TYPE_ORTHO_PROJECTION: geo_process_ortho_projection ((struct GraphNodeOrthoProjection *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_PERSPECTIVE: geo_process_perspective ((struct GraphNodePerspective *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_MASTER_LIST: geo_process_master_list ((struct GraphNodeMasterList *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_LEVEL_OF_DETAIL: geo_process_level_of_detail ((struct GraphNodeLevelOfDetail *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_SWITCH_CASE: geo_process_switch ((struct GraphNodeSwitchCase *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_CAMERA: geo_process_camera ((struct GraphNodeCamera *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_TRANSLATION_ROTATION: geo_process_translation_rotation((struct GraphNodeTranslationRotation *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_TRANSLATION: geo_process_translation ((struct GraphNodeTranslation *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_ROTATION: geo_process_rotation ((struct GraphNodeRotation *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_OBJECT: geo_process_object ((struct Object *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_ANIMATED_PART: geo_process_animated_part ((struct GraphNodeAnimatedPart *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_BILLBOARD: geo_process_billboard ((struct GraphNodeBillboard *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_DISPLAY_LIST: geo_process_display_list ((struct GraphNodeDisplayList *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_SCALE: geo_process_scale ((struct GraphNodeScale *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_SHADOW: geo_process_shadow ((struct GraphNodeShadow *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_OBJECT_PARENT: geo_process_object_parent ((struct GraphNodeObjectParent *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_GENERATED_LIST: geo_process_generated_list ((struct GraphNodeGenerated *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_BACKGROUND: geo_process_background ((struct GraphNodeBackground *) curGraphNode); break;
|
||||
case GRAPH_NODE_TYPE_HELD_OBJ: geo_process_held_object ((struct GraphNodeHeldObject *) curGraphNode); break;
|
||||
default: geo_try_process_children ((struct GraphNode *) curGraphNode); break;
|
||||
}
|
||||
GeoProcessJumpTable[curGraphNode->type](curGraphNode);
|
||||
}
|
||||
} else {
|
||||
if (curGraphNode->type == GRAPH_NODE_TYPE_OBJECT) {
|
||||
|
||||
Reference in New Issue
Block a user