Jump to content

Home

How Do I Get An NPC To Resume Its Actions After A Dialog


Ulic and Cay

Recommended Posts

I wrote the below script for an NPC and have it fire OnHeartbeat.

void sub1(int intParam1) {
if ((!GetIsConversationActive())) {
	switch (intParam1) {
		case 0:
			BarkString(OBJECT_SELF, StrRef0);
			break;
		case 1:
			BarkString(OBJECT_SELF, StrRef1);
			break;
		case 2:
			BarkString(OBJECT_SELF, StrRef2);
			break;
	}
}
}

void main() {
if ((!GetLocalBoolean(OBJECT_SELF, 5))) {
	SetLocalBoolean(OBJECT_SELF, 5, 1);
	ClearAllActions();
	ActionWait(4.0);
	ActionMoveToObject(GetObjectByTag("WP_YIMA_FUTZ1", 0), 0, 1.0);
	ActionPlayAnimation(102, 1.0, 1.0);
	ActionWait(5.0);
	ActionMoveToObject(GetObjectByTag("WP_YIMA_FUTZ2", 0), 0, 1.0);
	ActionPlayAnimation(103, 1.0, 1.0);
	ActionDoCommand(sub1(0));
	ActionWait(4.0);
	ActionMoveToObject(GetObjectByTag("WP_YIMA_FUTZ1", 0), 0, 1.0);
	ActionWait(4.0);
	ActionMoveToObject(GetObjectByTag("WP_YIMA_FUTZ3", 0), 0, 1.0);
	SetFacingPoint(GetPositionFromLocation(GetLocation(GetObjectByTag("WP_LOOK_07"))));
	ActionPlayAnimation(5, 1.0, -1.0);
	ActionWait(1.0);
	ActionDoCommand(sub1(1));
	ActionPlayAnimation(102, 1.0, 1.0);
	ActionWait(3.0);
	ActionMoveToObject(GetObjectByTag("WP_COM_YIMA", 0), 0, 1.0);
	ActionWait(4.0);
	SetFacingPoint(GetPositionFromLocation(GetLocation(GetObjectByTag("WP_COM_YIMA"))));
	ActionDoCommand(sub1(2));
	ActionPlayAnimation(5, 1.0, -1.0);
	ActionDoCommand(SetLocalBoolean(OBJECT_SELF, 5, 0));
}
}

It works fine but if I interrupt the NPC by initiating a dialog, when the dialog ends the NPC just stands there. How can I set it up so that the NPC will return to what it was doing before I initiated the dialog?

Link to comment
Share on other sites

I wrote the below script for an NPC and have it fire OnHeartbeat.
void main() {
if ((!GetLocalBoolean(OBJECT_SELF, 5))) {
	SetLocalBoolean(OBJECT_SELF, 5, 1);
(snip)
	ActionDoCommand(SetLocalBoolean(OBJECT_SELF, 5, 0));
}
}

It works fine but if I interrupt the NPC by initiating a dialog, when the dialog ends the NPC just stands there. How can I set it up so that the NPC will return to what it was doing before I initiated the dialog?

 

The problem is how you handle the flow control of the script. Since a heartbeat script runs roughly every 3 seconds you use a LocalBoolean to block your long sequence of actions from overlapping, and then reset the boolean as the final action.

 

The problem with this is that if the NPC is interrupted for any reason that causes its action queue to be cleared (combat, dialog, etc) your LocalBoolean will never be reset since the action that resets it gets flushed from the action queue before it has a chance to run.

 

There are a couple of ways around this that I can think of:

  1. Modify the OnDialogEnd event script to reset this LocalBoolean to FALSE whenever the NPC exits dialog. Also modify the OnCombatRound event script to reset the LocalBoolean to FALSE whenever the NPC enters combat.
     
     
  2. Modify your heartbeat script not to queue the whole sequence at once, but rather take advantage of the repeating nature of a heartbeat script to perform one step at a time, and then use a LocalNumber as a step counter to indicate how far along the sequence the NPC has come. Then the whole sequence wouldn't be flushed if the action queue is cleared, and at most the NPC would repeat the interrupted step again before moving on to the next.

Link to comment
Share on other sites

That second solution is exactly what I was looking for. Thanks a ton. I tried it out and it works, however, my NPC won't stop moving around now during the dialog. Here's a shortened version of what I think you're suggesting my script should look like. Let me know if this is what you had in mind and if you can come up with another neat way for me to stop my NPC from moving while I'm talking to her.

void main() {
int iLN = GetLocalNumber(OBJECT_SELF, 12);
if ((iLN == 0))) {
	ClearAllActions();
	ActionWait(4.0);
	SetLocalNumber(OBJECT_SELF, 12, 1);
}
else {
	if ((iLN == 1)) {
		ActionMoveToObject(GetObjectByTag("WP_YIMA_FUTZ1", 0), 0, 1.0);
		SetLocalNumber(OBJECT_SELF, 12, 2);
	}
	else {
		if ((iLN == 2)) {
			ActionPlayAnimation(102, 1.0, 1.0);
			ActionWait(5.0);
			SetLocalNumber(OBJECT_SELF, 12, 3);
		}
		else {
			if ((iLN == 3)) {
				SetLocalNumber(OBJECT_SELF, 12, 0);
			}
		}
	}
}
}

Link to comment
Share on other sites

That second solution is exactly what I was looking for. Thanks a ton. I tried it out and it works, however, my NPC won't stop moving around now during the dialog.

 

You can use the GetIsInConversation() and GetIsInCombat() functions to check if the character is in conversation or in combat to block out the rest of your actions in the meanwhile.

Link to comment
Share on other sites

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...