Rename door functions and add docblocks

This commit is contained in:
Ryan Dwyer 2021-03-01 12:08:39 +10:00
parent 506f3223f6
commit b1bfdbe6b6
9 changed files with 98 additions and 58 deletions

View File

@ -22736,7 +22736,7 @@ glabel var7f1a9260
/* f045b60: 00002825 */ or $a1,$zero,$zero
/* f045b64: 14400008 */ bnez $v0,.L0f045b88
/* f045b68: 24050001 */ addiu $a1,$zero,0x1
/* f045b6c: 0fc23922 */ jal doorActivate
/* f045b6c: 0fc23922 */ jal doorsRequestMode
/* f045b70: 8e040004 */ lw $a0,0x4($s0)
/* f045b74: 10000005 */ b .L0f045b8c
/* f045b78: 8fbf002c */ lw $ra,0x2c($sp)

View File

@ -111,7 +111,7 @@ bool (*g_CommandPointers[])(void) = {
/*0x0062*/ aiIfObjectHealthy,
/*0x0063*/ aiIfChrActivatedObject,
/*0x0064*/ NULL,
/*0x0065*/ ai0065,
/*0x0065*/ aiObjInteract,
/*0x0066*/ aiDestroyObject,
/*0x0067*/ ai0067,
/*0x0068*/ aiChrDropItems,

View File

@ -2198,14 +2198,14 @@ bool aiIfChrActivatedObject(void)
/**
* @cmd 0065
*/
bool ai0065(void)
bool aiObjInteract(void)
{
u8 *cmd = g_Vars.ailist + g_Vars.aioffset;
struct defaultobj *obj = objFindByTagId(cmd[2]);
if (obj && obj->prop) {
if (obj->prop->type == PROPTYPE_DOOR) {
doorActivateWrapper(obj->prop, 0);
doorsActivate(obj->prop, false);
} else if (obj->prop->type == PROPTYPE_OBJ || obj->prop->type == PROPTYPE_WEAPON) {
propobjInteract(obj->prop);
}
@ -2404,7 +2404,7 @@ bool aiOpenDoor(void)
if (obj && obj->prop && obj->prop->type == PROPTYPE_DOOR) {
if (!doorCallLift(obj->prop, false)) {
struct doorobj *door = (struct doorobj *) obj;
doorActivate(door, DOORMODE_OPENING);
doorsRequestMode(door, DOORMODE_OPENING);
}
}
@ -2423,7 +2423,7 @@ bool aiCloseDoor(void)
if (obj && obj->prop && obj->prop->type == PROPTYPE_DOOR) {
struct doorobj *door = (struct doorobj *) obj;
doorActivate(door, DOORMODE_CLOSING);
doorsRequestMode(door, DOORMODE_CLOSING);
}
g_Vars.aioffset += 3;

View File

@ -331,14 +331,15 @@ u32 var80069d00 = 0x00000000;
* if the caller should proceed with opening or closing the door. A true return
* doesn't necessarily mean the lift was called.
*
* If onlyifclosed is false, the lift can be called even if the given door is
* open... which seems weird, because lift doors can't be open if the lift isn't
* already there.
* The allowclose argument determines whether the door should be closed if the
* lift is at the door. This is typically true when the player has activated the
* door, and false when NPCs have activated the door. If true, doorCallLift
* doesn't handle the activation which allows the caller to close the door.
*
* Lifts will not be called if it's occupied by anyone. This prevents chrs from
* from calling lifts back when players are in them.
*/
bool doorCallLift(struct prop *doorprop, bool onlyifclosed)
bool doorCallLift(struct prop *doorprop, bool allowclose)
{
struct doorobj *door = doorprop->door;
bool handled = false;
@ -353,11 +354,15 @@ bool doorCallLift(struct prop *doorprop, bool onlyifclosed)
handled = true;
if (type == OBJTYPE_DOOR) {
// Unsure if reachable... I don't think the link->lift
// property is ever set to a door obj.
doorActivateWrapper(link->lift, onlyifclosed);
// This appears to be handling situations where the setup
// file specifies a door as the lift object. It activates
// that door, which then calls doorCallLift. This allows
// setup files to chain lift doors to other lift doors
// rather than directly to the lift, but this doesn't happen
// in practice so this branch is unused.
doorsActivate(link->lift, allowclose);
} else if (type == OBJTYPE_LIFT) {
if (onlyifclosed && door->base.type == OBJTYPE_DOOR && !doorIsClosed(door)) {
if (allowclose && door->base.type == OBJTYPE_DOOR && !doorIsClosed(door)) {
handled = false;
} else {
bool vacant = true;
@ -372,6 +377,10 @@ bool doorCallLift(struct prop *doorprop, bool onlyifclosed)
if (vacant) {
for (i = 0; i < numchrslots; i++) {
/**
* @bug: This is missing a chrIsDead check.
* If a chr dies in a lift it can no longer be called.
*/
if (g_ChrSlots[i].prop && g_ChrSlots[i].lift == link->lift) {
vacant = false;
break;
@ -19004,7 +19013,7 @@ glabel var7f1aa43c
.L0f077054:
/* f077054: 14600005 */ bnez $v1,.L0f07706c
/* f077058: 00000000 */ nop
/* f07705c: 0fc23922 */ jal doorActivate
/* f07705c: 0fc23922 */ jal doorsRequestMode
/* f077060: 02002025 */ or $a0,$s0,$zero
/* f077064: 1000002e */ b .L0f077120
/* f077068: 820a0084 */ lb $t2,0x84($s0)
@ -19056,7 +19065,7 @@ glabel var7f1aa43c
/* f07710c: 820a0084 */ lb $t2,0x84($s0)
.L0f077110:
/* f077110: 02002025 */ or $a0,$s0,$zero
/* f077114: 0fc23922 */ jal doorActivate
/* f077114: 0fc23922 */ jal doorsRequestMode
/* f077118: 24050002 */ addiu $a1,$zero,0x2
.L0f07711c:
/* f07711c: 820a0084 */ lb $t2,0x84($s0)
@ -19108,7 +19117,7 @@ glabel var7f1aa43c
/* f0771bc: 02002025 */ or $a0,$s0,$zero
/* f0771c0: 10400003 */ beqz $v0,.L0f0771d0
/* f0771c4: 8fa40078 */ lw $a0,0x78($sp)
/* f0771c8: 0fc23fba */ jal doorActivateWrapper
/* f0771c8: 0fc23fba */ jal doorsActivate
/* f0771cc: 00002825 */ or $a1,$zero,$zero
.L0f0771d0:
/* f0771d0: 3c0e800a */ lui $t6,%hi(g_Vars+0x8)
@ -19238,7 +19247,7 @@ glabel var7f1aa43c
// }
//
// if (hasflag == false) {
// doorActivate(door, DOORMODE_CLOSING);
// doorsRequestMode(door, DOORMODE_CLOSING);
// } else if (door->doorflags & DOORFLAG_0010) {
// // Check if any sibling has a false return value
// s32 pass = func0f08c040(door) == false;
@ -19259,7 +19268,7 @@ glabel var7f1aa43c
// loopdoor = loopdoor->sibling;
// }
// } else {
// doorActivate(door, DOORMODE_CLOSING);
// doorsRequestMode(door, DOORMODE_CLOSING);
// }
// }
// }
@ -19286,7 +19295,7 @@ glabel var7f1aa43c
// if (door->doortype == DOORTYPE_8
// && doorIsClosed(door)
// && doorIsPadlockFree(door)) {
// doorActivateWrapper(doorprop, false);
// doorsActivate(doorprop, false);
// }
//
// // Update frac
@ -19932,7 +19941,7 @@ void liftTick(struct prop *prop)
if (obj->flags & OBJFLAG_DEACTIVATED) {
move = false;
} else if (lift->doors[lift->levelcur] && !doorIsClosed(lift->doors[lift->levelcur])) {
doorActivate(lift->doors[lift->levelcur], DOORMODE_CLOSING);
doorsRequestMode(lift->doors[lift->levelcur], DOORMODE_CLOSING);
move = false;
}
@ -19996,7 +20005,7 @@ void liftTick(struct prop *prop)
door = lift->doors[lift->levelcur];
if (door && door->keyflags == 0) {
doorActivate(door, DOORMODE_OPENING);
doorsRequestMode(door, DOORMODE_OPENING);
}
}
@ -25562,7 +25571,7 @@ glabel var7f1aa6e4
/* f07d704: 0fc24030 */ jal func0f0900c0
/* f07d708: e7ac0058 */ swc1 $f12,0x58($sp)
/* f07d70c: 8fa401a0 */ lw $a0,0x1a0($sp)
/* f07d710: 0fc23922 */ jal doorActivate
/* f07d710: 0fc23922 */ jal doorsRequestMode
/* f07d714: 24050001 */ addiu $a1,$zero,0x1
/* f07d718: c7ac0058 */ lwc1 $f12,0x58($sp)
.L0f07d71c:
@ -26320,7 +26329,7 @@ glabel var7f1aa6e4
//
// if (dist < 200 * 200) {
// func0f0900c0(prop, door);
// doorActivate(door, DOORMODE_OPENING);
// doorsRequestMode(door, DOORMODE_OPENING);
// }
//
// if (dist < 195 * 195) {
@ -42615,7 +42624,7 @@ glabel func0f08c190
.L0f08c3d0:
/* f08c3d0: 12400003 */ beqz $s2,.L0f08c3e0
/* f08c3d4: 02c02025 */ or $a0,$s6,$zero
/* f08c3d8: 0fc23922 */ jal doorActivate
/* f08c3d8: 0fc23922 */ jal doorsRequestMode
/* f08c3dc: 24050001 */ addiu $a1,$zero,0x1
.L0f08c3e0:
/* f08c3e0: 86e20002 */ lh $v0,0x2($s7)
@ -44255,7 +44264,11 @@ void func0f08df10(s32 soundtype, struct prop *prop)
}
}
void func0f08e0c4(struct doorobj *door)
/**
* Play the door open sound, activate the door's portal,
* and configure the laser fade properties if it's a laser.
*/
void doorPrepareForOpen(struct doorobj *door)
{
door->base.flags &= ~OBJFLAG_DOOR_KEEPOPEN;
door->base.hidden |= OBJHFLAG_00000200;
@ -44281,17 +44294,17 @@ void func0f08e0c4(struct doorobj *door)
}
}
void func0f08e1a0(struct doorobj *door)
/**
* Play the door close sound and configure the
* laser fade properties if it's a laser.
*/
void doorPrepareForClose(struct doorobj *door)
{
door->base.flags &= ~OBJFLAG_DOOR_KEEPOPEN;
func0f08daa8(door->soundtype, door->base.prop);
if (door->doortype == DOORTYPE_LASER) {
door->fadetime60 = 60;
} else {
door->fadetime60 = 0;
}
door->fadetime60 = door->doortype == DOORTYPE_LASER ? 60 : 0;
if (door->doortype == DOORTYPE_LASER) {
door->laserfade = 0;
@ -44362,17 +44375,22 @@ void func0f08e2ac(struct doorobj *door)
#endif
}
/**
* Apply the given mode to an individual door (not its siblings).
*
* Handles playing door open/close sounds and activating the portal if opening.
*/
void doorSetMode(struct doorobj *door, s32 newmode)
{
if (newmode == DOORMODE_OPENING) {
if (door->mode == DOORMODE_IDLE || door->mode == DOORMODE_WAITING) {
func0f08e0c4(door);
doorPrepareForOpen(door);
}
door->mode = newmode;
} else if (newmode == DOORMODE_CLOSING) {
if (door->mode == DOORMODE_IDLE && door->frac > 0) {
func0f08e1a0(door);
doorPrepareForClose(door);
}
if ((door->mode != DOORMODE_IDLE && door->mode != DOORMODE_WAITING) || door->frac > 0) {
@ -44385,13 +44403,21 @@ void doorSetMode(struct doorobj *door, s32 newmode)
}
}
void doorActivate(struct doorobj *door, s32 newmode)
/**
* Request that the door and its siblings be applied the given mode
* (opening or closing).
*
* When opening an airlock-style door (eg. GE Dam gate), the requested mode is
* modified so that the sibling begins closing instead, and the main door waits
* for the sibling before it opens.
*/
void doorsRequestMode(struct doorobj *door, s32 newmode)
{
struct doorobj *loopdoor;
struct doorobj *sibling;
s32 siblingmode = newmode;
if ((door->base.flags2 & OBJFLAG2_40000000) && newmode == DOORMODE_OPENING) {
if ((door->base.flags2 & OBJFLAG2_AIRLOCKDOOR) && newmode == DOORMODE_OPENING) {
siblingmode = DOORMODE_CLOSING;
if (door->mode == DOORMODE_IDLE) {
@ -44401,11 +44427,11 @@ void doorActivate(struct doorobj *door, s32 newmode)
doorSetMode(door, newmode);
loopdoor = door->sibling;
sibling = door->sibling;
while (loopdoor && loopdoor != door) {
doorSetMode(loopdoor, siblingmode);
loopdoor = loopdoor->sibling;
while (sibling && sibling != door) {
doorSetMode(sibling, siblingmode);
sibling = sibling->sibling;
}
}
@ -46208,20 +46234,30 @@ bool doorTestForInteract(struct prop *prop)
return checkmore;
}
void doorActivateWrapper(struct prop *doorprop, bool arg1)
/**
* Activate the doors by calling the lift or requesting the new door mode
* (opening/closing) for the given door and its siblings.
*
* Assumes any lock checks have already been done and have passed.
*
* The allowliftclose argument determines whether the door should be closed if
* it's a lift door and the lift is at the door. This is typically true when the
* player has activated the door, and false when NPCs have activated the door.
*/
void doorsActivate(struct prop *doorprop, bool allowliftclose)
{
struct doorobj *door = doorprop->door;
if (!doorCallLift(doorprop, arg1)) {
if (!doorCallLift(doorprop, allowliftclose)) {
if (door->mode == DOORMODE_OPENING || door->mode == DOORMODE_WAITING) {
doorActivate(door, DOORMODE_CLOSING);
doorsRequestMode(door, DOORMODE_CLOSING);
} else if (door->mode == DOORMODE_CLOSING) {
doorActivate(door, DOORMODE_OPENING);
doorsRequestMode(door, DOORMODE_OPENING);
} else if (door->mode == DOORMODE_IDLE) {
if (door->frac > 0.5f * door->maxfrac) {
doorActivate(door, DOORMODE_CLOSING);
doorsRequestMode(door, DOORMODE_CLOSING);
} else {
doorActivate(door, DOORMODE_OPENING);
doorsRequestMode(door, DOORMODE_OPENING);
}
}
}
@ -46359,7 +46395,7 @@ bool propdoorInteract(struct prop *doorprop)
if (func0f08bd00(playerprop, doorprop)) {
func0f0900c0(playerprop, door);
doorActivateWrapper(doorprop, 1);
doorsActivate(doorprop, true);
} else if (door->mode == DOORMODE_IDLE && door->frac < 0.5f * door->maxfrac) {
if ((door->base.flags2 & OBJFLAG2_00000004) == 0) {
struct textoverride *override = invGetTextOverrideForObj(&door->base);

View File

@ -1621,7 +1621,7 @@ void frCloseAndLockDoor(void)
if (obj && obj->prop && obj->prop->type == PROPTYPE_DOOR) {
struct doorobj *door = (struct doorobj *)obj;
door->keyflags |= 0x40;
doorActivate(door, DOORMODE_CLOSING);
doorsRequestMode(door, DOORMODE_CLOSING);
}
}

View File

@ -945,8 +945,12 @@
object, \
label,
// Unused, and no idea what it does.
#define cmd0065(object) \
/**
* Interacts with the given object, as if the player pressed B on it.
*
* If the object is a door, lock checks are skipped.
*/
#define obj_interact(object) \
mkshort(0x0065), \
object,

View File

@ -2522,7 +2522,7 @@
#define OBJFLAG2_LOCKEDFRONT 0x08000000 // One-way door lock
#define OBJFLAG2_LOCKEDBACK 0x10000000 // One-way door lock
#define OBJFLAG2_AICANNOTUSE 0x20000000
#define OBJFLAG2_40000000 0x40000000 // Used by doors
#define OBJFLAG2_AIRLOCKDOOR 0x40000000 // Door waits for sibling to close before it can open
#define OBJFLAG2_80000000 0x80000000 // Attack Ship glass
// obj->flags3

View File

@ -104,7 +104,7 @@
/*0x0061*/ bool aiIfGunUnclaimed(void);
/*0x0062*/ bool aiIfObjectHealthy(void);
/*0x0063*/ bool aiIfChrActivatedObject(void);
/*0x0065*/ bool ai0065(void);
/*0x0065*/ bool aiObjInteract(void);
/*0x0066*/ bool aiDestroyObject(void);
/*0x0067*/ bool ai0067(void);
/*0x0068*/ bool aiChrDropItems(void);

View File

@ -27,7 +27,7 @@ void countdownTimerSetRunning(bool running);
void countdownTimerSetValue(f32 frames);
void countdownTimerSetVisible(u32 flag, bool show);
void countdownTimerTick(void);
bool doorCallLift(struct prop *doorprop, bool onlyifclosed);
bool doorCallLift(struct prop *doorprop, bool allowclose);
bool doorIsPadlockFree(struct doorobj *door);
bool objPassesSafePickupChecks(struct defaultobj *obj);
void objUpdateLinkedScenery(struct defaultobj *obj);
@ -314,13 +314,13 @@ void func0f08d784(s32 soundtype, struct prop *prop);
void func0f08daa8(s32 soundtype, struct prop *prop);
void func0f08dd44(s32 soundtype, struct prop *prop);
void func0f08df10(s32 soundtype, struct prop *prop);
void func0f08e0c4(struct doorobj *door);
void func0f08e1a0(struct doorobj *door);
void doorPrepareForOpen(struct doorobj *door);
void doorPrepareForClose(struct doorobj *door);
u32 decodeXorAaaaaaaa(u32 value);
void func0f08e224(struct doorobj *door);
void func0f08e2ac(struct doorobj *door);
void doorSetMode(struct doorobj *door, s32 newmode);
void doorActivate(struct doorobj *door, s32 newmode);
void doorsRequestMode(struct doorobj *door, s32 newmode);
s32 doorIsClosed(struct doorobj *door);
s32 doorIsOpen(struct doorobj *door);
s32 func0f08e5a8(s16 *rooms, struct screenbox *box);
@ -335,7 +335,7 @@ u32 func0f08f538(void);
u32 func0f08f604(void);
bool func0f08f968(struct doorobj *door, bool arg1);
bool doorTestForInteract(struct prop *prop);
void doorActivateWrapper(struct prop *prop, bool arg1);
void doorsActivate(struct prop *prop, bool allowliftclose);
u32 func0f08fffc(void);
void func0f0900c0(struct prop *prop, struct doorobj *door);
bool propdoorInteract(struct prop *doorprop);