Global script and object issues... (SOLVED)

Started by jfarwyke, Thu 14/05/2009 19:03:26

Previous topic - Next topic

jfarwyke

I want to run an object's animation after the player interacts with a NPC. First, I have the NPC walk to another part of the room, afterwards, I want the object to animate. The problem is, the global script doesn't recognize my object. What I did then is made my code in the global just for the NPC, then in the room I wrote a code for the object to run it's animation under certain conditions. But I don't know what function to place it under. I've tried Room Load after FadeIn and Repeatedly Execute, but to no avail.

Here's my global script code:
Code: ags
function cButt_Interact()
{
cPup.Walk(479, 218, eBlock);
cButt.Walk(500, 127);
cButt.AddWaypoint(557, 303);
cButt.AddWaypoint(441, 385);
cButt.AddWaypoint(37, 353);
cButt.Clickable = false;
}

And my Room code:
Code: ags
function room_AfterFadeIn()
{
if ((cButt.Clickable == false)&&(cButt.Moving == false)) {
  oFrogEatFly.SetView(16);
  oFrogEatFly.Animate(0, 0, eOnce, eBlock);
  cButt.ChangeRoom(2, 583, 450);
  oFrogEatFly.SetView(17);
  oFrogEatFly.Animate(0, 0, eOnce, eBlock);
  }
}

After the NPC walks to his location, nothing happens unless I leave the room and then come back again. Only then does the second code run.
Would the easiest thing be to simply make my object a character and handle it all in the global script? What am I doing wrong?

NsMn

#1
Actually, you should all put it into the character's Function and replace the objects' name (oFrogEatFly) with


Code: ags
object[x]


...,then it should work. Remember to replace the x with the objects' number.

jfarwyke

No, the object still doesn't animate. Here's the code:
Code: ags
function cButt_Interact()
{
cPup.Walk(479, 218, eBlock);
cButt.Walk(500, 127);
cButt.AddWaypoint(557, 303);
cButt.AddWaypoint(441, 385);
cButt.AddWaypoint(37, 353);
cButt.Clickable = false;
if ((cButt.Clickable == false)&&(cButt.Moving == false)) {
  object[0].SetView(16);
  object[0].Animate(0, 0, eOnce, eBlock);
  cButt.ChangeRoom(2, 583, 450);
  object[0].SetView(17);
  object[0].Animate(0, 0, eOnce, eBlock);
  cButt.Clickable = true;
  }
}

I have objects in other rooms also with the number 0, how does it know which object to animate?

jfarwyke

I threw a Wait command on there and now it works. I guess it tries to run the if stuff while my character is still walking, when it wouldn't meet the conditions. Initially, I thought when those conditions became available then it would run the rest of the script. My new code:
Code: ags
function cButt_Interact()
{
cPup.Walk(479, 218, eBlock);
cButt.Walk(500, 127);
cButt.AddWaypoint(557, 303);
cButt.AddWaypoint(441, 385);
cButt.AddWaypoint(37, 353);
Wait(280);
if (cButt.Moving == false) {
  object[0].SetView(16);
  object[0].Animate(0, 0, eOnce, eBlock);
  cButt.ChangeRoom(2, 583, 450);
  object[0].SetView(17);
  object[0].Animate(0, 0, eOnce, eBlock);
  }
}

However, I really don't like using Wait or any blocking because then the player expects something to happen and the eventuality of the frog eating the butterfly becomes obvious. If anyone knows a way or a trick to continue the gameplay during the butterfly's (cButt) long flight but not necessarily through my quick object animation, please let me know. Thanks.

jfarwyke

AHA HA HA! I did it! I gave my object an extra standing frame with a delay of 280 in place of the Wait command. It looks awesome. By the way NsMn, thanks for the tip about object
  • in the global, I'd still be lost without that. Until next time...

jfarwyke

NO! I was completely wrong. I still see that Wait cursor. I guess it's the blocking on the animation, I don't know. I just don't know anymore.

Matti

Of course, if you use the eBlock command, you aren't able to interact in any way and that's why the cursor changes to wait.

By the way, you can modify your post instead of posting four times in a row.

Khris

In general, if you want something to happen once at an arbitrary point in time, you'd put it inside a repeatedly_execute, in this case the room's (create the event for the room, this should add a function called "room_RepExec()" to your room script).

One way to trigger the event is by using a timer.
Instead of using Wait(280); you use SetTimer(1, 280);
This will make timer no. 1 count down in the background.

Inside the room's rep_ex, put:

Code: ags
  if (IsTimerExpired(1)) {
    object[0].SetView(16);
    object[0].Animate(0, 0, eOnce, eBlock);
    cButt.ChangeRoom(2, 583, 450);
    object[0].SetView(17);
    object[0].Animate(0, 0, eOnce, eBlock);
    cButt.Clickable = true;
  }

(You can use the object's name now instead of object[0].)

IsTimerExpired() will return true only once, then false again, so you don't need to worry about the code being executed more than once.

Trent R

Another way (actually, its a very specific rep_exec) is to use a region around the points 37, 353. (That is, if I'm understanding your script correctly). Then create a region's while_standing or walk_on function and put your code there.

QuoteIsTimerExpired() will return true only once, then false again, so you don't need to worry about the code being executed more than once.
Unless you reset the timer, so it probably wouldn't hurt to toss a DoOnceOnly in there too. (unless your certain you won't use timers again in your game/room)

~Trent
To give back to the AGS community, I can get you free, full versions of commercial software. Recently, Paint Shop Pro X, and eXPert PDF Pro 6. Please PM me for details.


Current Project: The Wanderer
On Hold: Hero of the Rune

jfarwyke

Kris' suggestions worked beautifully. I did not know about Timers. Thank you. As for Trent's suggestion of the DoOnceOnly, when I was reading about it in the manual, they present the example in an "if" statement, and was wondering where I would place it; in the room script or in the global? I'm just not very clear on that. Here's my two scripts as they are right now:

the global
Code: ags
function cButt_Interact()
{
cPup.Walk(479, 218, eBlock);
cButt.Walk(500, 127);
cButt.AddWaypoint(557, 303);
cButt.AddWaypoint(441, 385);
cButt.AddWaypoint(37, 353);
SetTimer(1, 280);
}

the room
Code: ags
function room_RepExec()
{
if (IsTimerExpired(1)) {
  oFrogEatFly.SetView(16);
  oFrogEatFly.Animate(0, 2, eOnce, eBlock);
  cButt.ChangeRoom(2, 583, 450);
  oFrogEatFly.SetView(17);
  oFrogEatFly.Animate(0, 2, eOnce);
  }
}

So I'm not very clear on how to use the DoOnceOnly, despite having read about it in the manual. Also, Trent, you mentioned the use of Regions. cButt is a NPC. Is it true that NPC's can activate regions? Because wouldn't the Region Function, WalksOnto, for example, apply only to the playable character? Sorry guys if I'm making this more complicated than it really is. I'm trying to understand scripting the best I can. And yes, Mr.Matti, I'll modify my posts from now on, I can see how multiple posts can be annoying and space consuming. Thanks guys.

Trent R

Oops, the region events only work for the player. However, you can use Region.GetAtRoomXY in the rep_exec (if you didn't want to wait for 280 frames, and just wanted it to happen when they got to the region).

The DoOnceOnly is to make sure it only happens once. If you never use Timer1 again, then you're fine. (You have 20 timers available).


Btw-I'm just throwing out other suggestions and ideas, but I do think that Khris's way is the best in this case. Never hurts to learn new functions and ways to use them.

~Trent
To give back to the AGS community, I can get you free, full versions of commercial software. Recently, Paint Shop Pro X, and eXPert PDF Pro 6. Please PM me for details.


Current Project: The Wanderer
On Hold: Hero of the Rune

jfarwyke

QuoteNever hurts to learn new functions and ways to use them.
True that. It's my wish to learn everything I possibly can. And you guys are a huge help. Thanks again.

SMF spam blocked by CleanTalk