Actors

From CloudModding MM Wiki
Jump to: navigation, search
See also: Category:Actors

Actors are the various interactive pieces in the Zelda 64 engine, from enemies to static scenery.

There are three major components to an actor:

  • The actor's overlay, a file that contains the code for an actor
  • Actor instances, or an in memory representation of our actor.
  • Object files, one or more files that contain pre-generated microcode, animations, and graphical assets for an actor. These can be shared by multiple actors.

Actor Overlay Table

For a list of the data within this table, see Actor List.
code (File)
Actor Overlay Table
Version VRom VRam Size
Debug DD5A50 ? ? ? 5640
US 1.0 C45510 ? 801AEFD0 ? 5640

The actor table manages the actor files (overlays). It defines an actor's number, maps the actor to a virtual address, and during gameplay is used to find the overlay in ram.

Format

xxxxxxxx yyyyyyyy aaaaaaaa bbbbbbbb
pppppppp iiiiiiii nnnnnnnn ????cc??

This breaks down into-
x y: Start/End Virtual Rom addresses of the actor file
a b: Start/End Virtual Ram addresses of the actor file
p: Ram address of actor file (00000000 if overlay isn't loaded, or if in ROM)
i: Virtual Ram address of the start of the actor instance initialization variables, located within the file
n: Address of actor filename (Debug ROM only, value is 0 in commercial roms)
c: Number of actor instances of this type currently loaded (ram only)

Note: The record for Link's actor in rom (the first record in the table) only sets the vram address that points to the start of the variable info for Link's actor, and the actor file name pointer if it's the Debug Rom.

Overlay File

See Overlays for more information on the overlay format.

Initialization Variables

The actor's initialization variables are pointed to via the 6th word in the Actor Overlay Table.

/*0x00*/ short ActorNumber //value does not always match the instance's real actor number
/*0x02*/ byte  ActorType //See Below
/*0x03*/ byte  RoomNumber //Room instance was spawned in. If value set to FF in rom, instance does not despawn when swapping rooms

//0x04 is unknown
/*0x08*/ short ObjectNumber //possibly it's primary object dependency
//0x0A Padding

/*0x0C*/ int InstanceSize
/*0x10*/ int* ?
/*0x14*/ int* Deconstructor
/*0x18*/ int* ?
/*0x1C*/ int* ?

Common Data Structures

Actor Instances

typedef struct {
	f32 x, y, z;
} Coord;

typedef struct {
	u16 x, y, z;
} rotation;

typedef struct
{
    /* !0x00 */ u16 actorNo;
    /* !0x02 */ u8 actorType;
    /* !0x03 */ u8 roomNo; //Room number the actor is part of. FF denotes that the actor won't despawn on a room change
    /* 0x04 */ u32 unk_01;
    /* !0x08 */ Coord Pos1; //Related to collision detection routine
    /* !0x14 */ rotation initRot;
    /* 0x1A */ u16 unk_02;
    /* !0x1C */ u16 actorVariable;
    /* 0x1E */ u16 unk_03;
    /* 0x20 */ u16 soundEffect; //Plays sound effect (relative to actor's location, if within range of camera?) 
    /* 0x22 */ u16 unk_04;
    /* 0x24 */ Coord Pos2; //Current coordinate
    /* 0x30 */ u16 unk_04_a;
    /* 0x32 */ u16 unk_04_b;
    /* 0x34 */ char buff[4];
    /* 0x38 */ Coord Pos3;
    /* 0x44 */ rotation rot_1;
    /* 0x4A */ u16 unk_05;
    /* 0x4C */ f32 unk_06; /* I know this is a float from breakpointing it */
    /* 0x50 */ Coord Scale;
    /* 0x5C */ char buff2[0x58];
    /* !0xBC */ rotation rot_2; //Setting this immediately changes actor's rotation
    /* ? */ char buff3[0x66];
    /* 0x115 */ u8 runActor; // Determines if actor instance should be processed. 01 for yes, 00 for no.
    /* !0x128 */ z_ram_actor* actor_prev; /* Previous z_ram_actor of this type */
    /* !0x12C */ z_ram_actor* actor_next; /* Next z_ram_actor of this type */
    /* ? */ u32 unk; //Actor Constructor?
    /* ? */ u32 ActorInit; //Actor Deconstructor?
    /* ? */ u32 ActorDraw;
    /* ? */ u32 ActorMain;
    /* ? */ u32 CodeEntry; //Address to source overlay file's reference in code (file)
    /* ? */
    /* From here on, the structure and size varies for each actor */
} z_ram_actor;

/* 8-10-2012 : Addition made by Jason777 */
/* For actors which contain a damage chart (example: Stalfos)... */
typedef struct
{
     ..
     /* !0xA0 */ u32 DamageChart;  /* Pointer to the actor's Damage Chart in RAM. */
     ..
     /* !0xB7 */ u8 Health; //probably actually a short
     /* ?0xB9 */ u8 DamageEffect; //Stores what effect should occur when hit by a weapon
     ..
} z_ram_actor;

Categories

Actor instances are added into a doubly-linked list based on a category id. Ids can be set in the overlay file, but can also be pro grammatically modified (ex. Skulltula/Gold Skulltula actor). There are 12 categories total. Majora's Mask may use 16 different categories.

char * actor_types[12] = {
    "Switch",	"Prop (1)",	"Player",	"Bomb",
    "NPC",	"Enemy",	"Prop (2)",	"Item/Action",
    "Misc",	"Boss",		"Door",		"Chests"
};
Id Description Usage
0 Switches Step-on switches, Anubis enemy, Death Mountain Crater Smoke Cone
1 Prop (1) Typically larger, more complex set pieces
2 Player
3 Bomb Bombs, Bombchus
4 NPC
5 Enemy Used for triggering room clear state.
6 Prop
7 Item/Action
8 Misc
9 Boss
10 Door
11 Chests

Loading Actors

What is currently known about the loading and execution of code from actors in Zelda 64 is that:

  • The first time an actor is loaded (spawned), its overlay file is transferred to RAM
    • The transferred file has its offsets relocated to a real address space in RAM
    • The actor file remains allocated in ram until all instances of that actor have despawned
  • The game begins to create an instance of the actor
  • For each actor instance, actors are given a certain amount of memory as defined in the actor file. However, the minimum space required by the game's engine is 0x128 bytes in OoT (MM may vary).
    • Within this given memory is information such as
      • Location
      • Rotation
      • Scale
      • Pointer to damage chart (if the actor has one)
      • Pointers to actor functions
        • Initialization - run when actor instance is loaded.
        • Main - always run during gameplay.
        • Drawing - to be run when actor is close enough to the camera.
      • Pointer to Next/Previous actor(s) of this actor's category
      • Whatever else that actor needs (ex. instanced variables).

At Global Context + 0x1CB0 is a list of actor categories (see above), each element structured as follows:

int numOfActors;
ptr firstActor;
int unknown;

The pointer points to the first allocated entry for an actor. The integer is the number of actors of that category, the first entry being type 0, and the last last being type 11 (chests). Actors after the first actor are pointed to through the next/previous pointers within each allocated actor.

Custom Actors

A number of custom actors have been created. For more information, see Overlays.

Examples

Every actor in Debug MQ disassembled

Credits

Cendamos - Actor table information, misc stuff that got the ball rolling
Euler - Actor file structure
JayTheHam - His early work with Cendamos on actor information
ZZT32 - Explained some actor table stuff to me
spinout - Writing this article