Author Topic: need help with distanceTo and how to stop ego  (Read 5879 times)

0 Members and 1 Guest are viewing this topic.

Offline stateofpsychosis

need help with distanceTo and how to stop ego
« on: November 18, 2014, 01:42:47 PM »
okay so i'm working on a time bomb where if it's armed and you are close enough to it you die
but if you aren't close enough it just blows up and disappears. it's giving me some trouble.
when i use distanceTo it only triggers the death handler when i make the ego move. if he's close enough but standing still, it doesn't activate.

Also, having trouble programming the ego to just stop moving. that one should be simple once I know the correct code to use.

anyways, here's what I have so far...

the players said inputs:

Code: [Select]
(if(Said('drop/timebomb')) // whatever item1 is of course
  (if(send gEgo:has(18)) // check that ego has the item to begin with
  Print("You drop the time bomb.") // let them know it's dropped
  = inventory2Room scriptNumber // set the global variable, so it remembers where item 1 was dropped
  = inventory2X (+ (send gEgo:x) 3) // set the global variable, so it remembers the x posn of where it was dropped
  = inventory2Y (+ (send gEgo:y) 3) // set the global variable, so it remembers the y posn of where it was dropped
  (send gEgo:put(18))// get the item out of the users inventory
  (inventory2View:init()posn((send gEgo:x) (+ (send gEgo:y) 3))) // init the item right now
 )
  (else Print("You don't have that to drop."))
) // end said drop item



(if(Said('arm/timebomb'))
(if(> (send gEgo:distanceTo(inventory2View)) 15)
(if(< (send gEgo:distanceTo(inventory2View)) 30)
Print("You light the cigarette on the time bomb.")
(send gEgo:setScript(arm2Script))
)(else
Print("You're too far away. Get closer.")
))(else Print("You are too close. Back up a little."))

)
      
the main script global variables:      

Code: [Select]
inventory2Room = 0

inventory2X = 0
inventory2Y = 0


the global variable initializations in the room script:


   
Code: [Select]
(if(== inventory2Room scriptNumber)(inventory2View:init()posn(inventory2X inventory2Y)))

the instance for the bomb:

Code: [Select]
(instance inventory2View of Prop(properties x 400 y 400 view 38 loop 0 cel 1))

and the part i need help with...

the scripts for everything else:


Code: [Select]
(instance arm2Script of Script
(properties)
  (method (changeState newState)
  
  = state newState
    (switch (newState)
    (case 0
     = cycles 50)
    (case 1
     (send gEgo:setScript(boom2Script))
     = cycles 0)
 
  )
 ))



(instance boom2Script of Script
(properties)
  (method (changeState newState)
  
  = state newState
    (switch (newState)
     (case 0
    
     = cycles 1)
    
    (case 1 (inventory2View:view(34)setCycle(Fwd) loop(0))
        
                = cycles 3
) ))
(method (handleEvent pEvent)
  (var dyingScript)
(super:handleEvent(pEvent))
    
     (if(< (send gEgo:distanceTo(inventory2View)) 50)
     (if(== inventory2Room scriptNumber) // make sure it is here to begin with

      ProgramControl()
     (send gEgo:setMotion(MoveTo inventory2View))
        (send gEgo:view(37)setCycle(Fwd) loop(0))
     = dyingScript ScriptID(DYING_SCRIPT)
  (send dyingScript:
    caller(36)
    register("You blew yourself up. Good job. Way to die!")
  )
  (send gGame:setScript(dyingScript))
  PlayerControl()
    = inventory2Room 0// reset the global variable
     = inventory2Y 0 // reset the global variable
     = inventory2Y 0 // reset the global variable
     (inventory2View:posn(400 400)hide()) // get the item view off screen
    
))(else
 = inventory2Room 0// reset the global variable
     = inventory2Y 0 // reset the global variable
     = inventory2Y 0 // reset the global variable
     (inventory2View:posn(400 400)hide()) // get the item view off screen
    


)))
     
          

definitely made some mistake somewhere or doing something the wrong way. I'm thinking I probably have to set up an if for a rectangle that's based off the inventory2x and inventory2y variables but have no clue how that's done.

also need to know how to stop the ego, because making him 'moveTo' the position of the bomb is only working on the mine i have set up that works... not this one for some reason.

(i know i didn't need the two change state methods. just where i'm left after trying tons of different stuff)

 now trying to set up that rectangle using the global variables by add two more
 = inventory2X2 (+ (send gEgo:x) 30)
  = inventory2Y2 (+ (send gEgo:y) 30)

and like this:
       (if(send gEgo:inRect(inventory2X inventory2Y inventory2X2 inventory2Y2))

not working though
« Last Edit: November 18, 2014, 03:58:21 PM by stateofpsychosis »



Offline Cloudee1

Re: need help with distanceTo and how to stop ego
« Reply #1 on: November 18, 2014, 08:03:26 PM »
I am not really sure what it is that you are trying to do exactly, but here goes...

To stop the ego from moving. In the ProgramControl() procedure or function as it would be known in any other language, there is this:

Code: [Select]
(send gEgo:setMotion(NULL))

This will stop the ego from moving. You don't really need it though if you call ProgramControl() because it will stop the ego for you. But if you do want to stop the ego anytime, that is how it is done. Likewise, just for info, if you ever want to stop a views animation you could send a call of setCycle(NULL).

There are some issues with your boomScript that you have posted here. I see that you have some stuff going on listed under a Handle Event method. The handle event method is primarily used to handle the user events, or more specifically the user's input events such as mouse clicks or typed commands like look room. Judging from what you have there. It almost looks like you would be better off with a doit method. That's the assumption that I am going to work under anyway.

So here goes with what it is I think you are trying to accomplish... Let me know if I have it wrong at all and I will adjust my example accordingly. So you have a bomb, item 18, and you can drop the bomb anywhere a la the code we worked out a few days ago. Now you want to be able to set off this bomb using a cigarette. After a few seconds or cycles the bomb goes off and depending on how close ego is as to whether or not he is affected.... I am assuming that the bombs placement is still up and working fine.

Now assuming that I have the scenario right, it sounds like we are going to need a couple of local variables assuming of course that the ego is not going to be able to leave the room until after this bomb goes off. Leaving the room and coming back would be a slightly different approach using globals and a timer etc. So for this, I am assuming local variables... Right after the uses("") at the top of the script and before the first instance:

Code: [Select]
(local
  bombArmed = FALSE // has the bomb been armed
  bombAble = FALSE // bomb has been armed and is ready to blow
)

Looking at your said statements, they seem to be in relative good order. I am going to rewrite the said arm bomb a bit, to include this new local variable.

Code: [Select]
(if(Said('arm/timebomb'))
 (if(bombArmed)Print("The bomb is already lit, you should probably stay clear of it."))
 (else // bomb not armed yet
   (if(> (send gEgo:distanceTo(inventory2View)) 15)
    (if(< (send gEgo:distanceTo(inventory2View)) 30)
    Print("You light the cigarette on the time bomb.")
    = bombArmed TRUE
    (send gEgo:setScript(boom2Script))
    )
    (else Print("You're too far away. Get closer."))// more than 30 away
   )
   (else Print("You are too close. Back up a little."))// closer than 15
 )
) // ends said arm timebomb

If you notice, I went ahead and bypassed the armScript, because just like you said, you don't need them both. Now here goes my attempt at your boomScript.

Code: [Select]
(instance boom2Script of Script
(properties)
  (method (changeState newState)
  = state newState
    (switch (newState)
      (case 0 = cycles 1)
      (case 1 (inventory2View:view(34)setCycle(Fwd) loop(0)) // I am assuming that this is fuse burning view
                  = seconds 5)// how long before bomb is ready to explode
      (case 2 = bombAble TRUE)// Tells our doit method to trigger...
    ) // end switch
  )// end method
  //**************************************
  (method (doit)  // using a doit method to explode the bomb...
  (var dyingScript)
  (super:doit())
    (if(bombAble) // the timer on bomb has been reached ... it will do what follows
      = bombAble FALSE // we only want to do it once, so turn this trigger variable back off
      (if(< (send gEgo:distanceTo(inventory2View)) 50)
        ProgramControl() // This should stop the ego if they are walking... if not you know what to do
         // (send gEgo:setMotion(MoveTo inventory2View)) // not sure what this is doing here... going towards bomb?
    (send gEgo:view(37)setCycle(End)cel(0)loop(0)) // again not sure what this view is doing, guessing bomb blowing up!!
    = dyingScript ScriptID(DYING_SCRIPT)
         (send dyingScript:
         caller(36)
         register("You blew yourself up. Good job. Way to die!")
         )
        (send gGame:setScript(dyingScript))
      )// ends ego exploded....
      (else
          // ego more than 50 away... do nothing
      )
   = inventory2Room 0// reset the global variable
   = inventory2Y 0 // reset the global variable
   = inventory2Y 0 // reset the global variable
   (inventory2View:posn(400 400)hide()) // get the item view off screen
   )
  )// end method 

Ok, so assuming I have the scenario even halfway right, that should get you an exploding bomb that only effects ego if they are less than 50 away and occurs 5 seconds after the fuse has been lit.

But you mentioned using a rectangle to test for distance, not distance to. There are a few ways to do that, the simplest would be to just use your current global variables and do some math on them at runtime rather that set up new globals...

So here is the syntax for the in rectangle. Looking at the code you have posted, I am not really sure why yours isn't working. It seems sound. My only guess might be the 30 you are adding, that is actually pretty small rectangle all things considered. The ego is 20 wide itself. Oh also, as you have it, one corner of your rectangle is the corner of the bomb, so it is only looking at a rectangle to the below and to the right of the inventory2 view, not a rectangle around the bomb.

Anyway, without adding any new variables that we really don't need,

Code: [Select]
(if(send gEgo:inRect((- inventory2X 50) (- inventory2Y 25) (+ inventory2X  50) (+ inventory2Y 50)))

)// end ego in rectangle


 

« Last Edit: November 18, 2014, 08:09:28 PM by Cloudee1 »
Halloween Competition Brass Lantern Prop Competition Groundhog Day Competition

Offline stateofpsychosis

Re: need help with distanceTo and how to stop ego
« Reply #2 on: November 19, 2014, 10:11:47 AM »
yep that worked.


so I had to do a bit of changing just so the animations played for the right amount of time.. that fuse view was actually an explosion view but I added a fuse burning view too because that was a good idea :)

Code: [Select]
(instance boom2Script of Script
(properties)
  (method (changeState newState)
  = state newState
    (switch (newState)
      (case 0
       (inventory2View:view(39)setCycle(Fwd) loop(0)) //fuse burning view
       = seconds 6)// how long before bomb is ready to explode
      (case 1 (inventory2View:view(34)setCycle(Fwd) loop(0)) // explosion view
               = cycles 5 )
      (case 2 = bombAble TRUE)// Tells our doit method to trigger...
        
    ) // end switch
  )// end method
  //**************************************
  (method (doit)  // using a doit method to explode the bomb...
  (var dyingScript)
  (super:doit())
    (if(bombAble) // the timer on bomb has been reached ... it will do what follows
      = bombAble FALSE // we only want to do it once, so turn this trigger variable back off
      (if(send gEgo:inRect((- inventory2X 30) (- inventory2Y 30) (+ inventory2X  30) (+ inventory2Y 30)))
        ProgramControl()
        (send gEgo:setMotion(NULL))
        // This should stop the ego if they are walking... if not you know what to do
       // (send gEgo:setMotion(MoveTo inventory2View)) // not sure what this is doing here... going towards bomb?
     (send gEgo:view(37)setCycle(End)cel(0)loop(0)) // again not sure what this view is doing, guessing bomb blowing up!!
     = dyingScript ScriptID(DYING_SCRIPT)
         (send dyingScript:
         caller(36)
         register("You blew yourself up. Good job. Way to die!")
         )
        (send gGame:setScript(dyingScript))
      )// ends ego exploded....
      (else
          // ego more than 50 away... do nothing
 )
   = inventory2Room 0// reset the global variable
   = inventory2Y 0 // reset the global variable
   = inventory2Y 0 // reset the global variable
   (inventory2View:posn(400 400)hide()) // get the item view off screen
   )
))


also had to update the said input a bit because I realized i missed something
(forgot to make it check that the bomb was actually there first :P)

Code: [Select]
(if(Said('arm/timebomb'))
(if(== inventory2Room scriptNumber)
 (if(bombArmed)Print("The bomb is already lit, you should probably stay clear of it."))
 (else // bomb not armed yet
   (if(> (send gEgo:distanceTo(inventory2View)) 15)
    (if(< (send gEgo:distanceTo(inventory2View)) 30)
    Print("You light the cigarette on the time bomb.")
    = bombArmed TRUE
    (send gEgo:setScript(boom2Script))
    )
    (else Print("You're too far away. Get closer."))// more than 30 away
   )
   (else Print("You are too close. Back up a little."))// closer than 15
 )
)(else Print("You don't see that here."))) // ends said arm timebomb



only problems it has now are:
1. if you try to drop more than one bomb at once it just removes the first one and adds another.
2. if you try to drop another bomb after the first one explodes.. it says it works but the view doesn't show up.. then if you leave the room and come back it's there where you dropped it.. strange..

those aren't major problems though
oh and I don't think I'll bother making the armed variables global.. leaving the room and coming back will just turn off the bombs which is kind of ideal since someone could save in a way where they'll die if they come back in the room leaving dead ends in the game.. so think it's best to keep them local i guess.
thanks for the help yet again!

now i just have to program them so they also kill the actors or should i say killer robots who run into them. that'll be on a room to room basis i guess. should be pretty strait forward :)
« Last Edit: November 19, 2014, 10:38:55 AM by stateofpsychosis »

Offline Cloudee1

Re: need help with distanceTo and how to stop ego
« Reply #3 on: November 19, 2014, 11:16:49 AM »
As for dropping the bomb... multiple times, it sounds like we went astray somewhere with the drop bomb said statement. that may need to be revisited. Sounds like both of the issues should be able to fixed there. But looking at the code you have posted, I would think that we would be good since the first check is to see if the user has item number 18, and if they do then we take it away as part of the statement. That should prevent them from dropping twice... strange

...or do they have more than one bomb that they are able to drop?
« Last Edit: November 19, 2014, 11:19:22 AM by Cloudee1 »
Halloween Competition Brass Lantern Prop Competition Groundhog Day Competition

Offline stateofpsychosis

Re: need help with distanceTo and how to stop ego
« Reply #4 on: November 19, 2014, 11:24:39 AM »
well eventually I wanted to have more than one of certain items like this.. sort of doing something similar to quest for glory but only everything kills you in one shot like real life


it's also a problem for when they pick up the bomb again and decide to replace it
the view shows up blank on the 2nd time just the same but it acts as if it's still there.

yea, definitely fudged something that's hard to see in there
probably right it's in the said input

Offline stateofpsychosis

Re: need help with distanceTo and how to stop ego
« Reply #5 on: November 20, 2014, 10:52:46 AM »
got it!

I had to add show() to the end of this line:

Code: [Select]
(inventory2View:init()posn((send gEgo:x) (- (send gEgo:y) 3))show())
was just a guess too :P

It was because the code was hiding the view after it either blew up or it was picked up with hide()

this fixes when you try to pick up the bomb and then drop it again so it doesn't show up as a blank view now, but still doesn't allow you to drop more than one.
I'll deal with that side of it later


« Last Edit: November 20, 2014, 10:55:08 AM by stateofpsychosis »


SMF 2.0.19 | SMF © 2021, Simple Machines
Simple Audio Video Embedder

Page created in 0.043 seconds with 22 queries.