Difference between revisions of "Reference Variables for Nearby Actors"

made everything work well on the wiki
imported>DragoonWraith
 
imported>DragoonWraith
(made everything work well on the wiki)
Line 1: Line 1:
Originally posted on [http://www.elderscrolls.com/forums/ Elder Scrolls Forums] by Tegid
Originally posted on [http://www.elderscrolls.com/forums/ Elder Scrolls Forums] by Tegid


I know there have been several people who have wanted to get references for the various enemies and actors in their area. Here are the steps to do this with the current set of Script commands.
I know there have been several people who have wanted to get references for the various enemies and actors in their area. Here are the steps to do this with the current set of Script commands.
Line 8: Line 10:
Now we need our script effect. This one is definitely not perfect (I don't seem to ever hit my ScriptFinishEffect, but it isn't necessary anyhow.)
Now we need our script effect. This one is definitely not perfect (I don't seem to ever hit my ScriptFinishEffect, but it isn't necessary anyhow.)


CODE
scriptname EntityFinderEffect
 
scriptname EntityFinderEffect
short NotReported
 
ref self
short NotReported
ref self
float timer
 
float timer
begin ScriptEffectStart
 
  set self to GetSelf
begin ScriptEffectStart
; message "Casting EntityFinderEffect", 20
    set self to GetSelf
  set timer to 0
;   message "Casting EntityFinderEffect", 20
  if (self != player)
    set timer to 0
    set NotReported to 1
    if (self != player)
  else
        set NotReported to 1
    set NotReported to 0
    else
  endif
        set NotReported to 0
end
    endif
end
begin ScriptEffectUpdate
 
  if (timer > 0)
begin ScriptEffectUpdate
    set timer to (timer - GetSecondsPassed)
    if (timer > 0)
    return
        set timer to (timer - GetSecondsPassed)
  else
        return
    set timer to 0.5
    else
  endif
        set timer to 0.5
  if (NotReported == 1)
    endif
    if (EnemyFinderRef1.RefsRequested == 0)
    if (NotReported == 1)
      set NotReported to 0
        if (EnemyFinderRef1.RefsRequested == 0)
    else
            set NotReported to 0
      if (EnemyFinderRef1.RefsRequested == 1)
        else
        if (EnemyFinderRef1.ref1full == 0)
            if (EnemyFinderRef1.RefsRequested == 1)
          set EnemyFinderRef1.ref1full to 1
              if (EnemyFinderRef1.ref1full == 0)
          set EnemyFinderRef1.reference1 to self
                set EnemyFinderRef1.ref1full to 1
;         Message "Reported to Reference1",1
                set EnemyFinderRef1.reference1 to self
          set NotReported to 0
;               Message "Reported to Reference1",1
        elseif (EnemyFinderRef1.ref2full == 0)
                set NotReported to 0
          set EnemyFinderRef1.ref2full to 1
              elseif (EnemyFinderRef1.ref2full == 0)
          set EnemyFinderRef1.reference2 to self
                set EnemyFinderRef1.ref2full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference2 to self
;         Message "Reported to Reference2",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref3full == 0)
;               Message "Reported to Reference2",1
          set EnemyFinderRef1.ref3full to 1
              elseif (EnemyFinderRef1.ref3full == 0)
          set EnemyFinderRef1.reference3 to self
                set EnemyFinderRef1.ref3full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference3 to self
;         Message "Reported to Reference3",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref4full == 0)
;               Message "Reported to Reference3",1
          set EnemyFinderRef1.ref4full to 1
              elseif (EnemyFinderRef1.ref4full == 0)
          set EnemyFinderRef1.reference4 to self
                set EnemyFinderRef1.ref4full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference4 to self
;         Message "Reported to Reference4",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref5full == 0)
;               Message "Reported to Reference4",1
          set EnemyFinderRef1.ref5full to 1
              elseif (EnemyFinderRef1.ref5full == 0)
          set EnemyFinderRef1.reference5 to self
                set EnemyFinderRef1.ref5full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference5 to self
;         Message "Reported to Reference5",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref6full == 0)
;               Message "Reported to Reference5",1
          set EnemyFinderRef1.ref6full to 1
              elseif (EnemyFinderRef1.ref6full == 0)
          set EnemyFinderRef1.reference6 to self
                set EnemyFinderRef1.ref6full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference6 to self
;         Message "Reported to Reference6",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref7full == 0)
;               Message "Reported to Reference6",1
          set EnemyFinderRef1.ref7full to 1
              elseif (EnemyFinderRef1.ref7full == 0)
          set EnemyFinderRef1.reference7 to self
                set EnemyFinderRef1.ref7full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference7 to self
;         Message "Reported to Reference7",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref8full == 0)
;               Message "Reported to Reference7",1
          set EnemyFinderRef1.ref8full to 1
              elseif (EnemyFinderRef1.ref8full == 0)
          set EnemyFinderRef1.reference8 to self
                set EnemyFinderRef1.ref8full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference8 to self
;         Message "Reported to Reference8",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref9full == 0)
;               Message "Reported to Reference8",1
          set EnemyFinderRef1.ref9full to 1
              elseif (EnemyFinderRef1.ref9full == 0)
          set EnemyFinderRef1.reference9 to self
                set EnemyFinderRef1.ref9full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference9 to self
;         Message "Reported to Reference9",1
                set NotReported to 0
        elseif (EnemyFinderRef1.ref10full == 0)
;               Message "Reported to Reference9",1
          set EnemyFinderRef1.ref10full to 1
              elseif (EnemyFinderRef1.ref10full == 0)
          set EnemyFinderRef1.reference10 to self
                set EnemyFinderRef1.ref10full to 1
          set NotReported to 0
                set EnemyFinderRef1.reference10 to self
;         Message "Reported to Reference10",1
                set NotReported to 0
        endif
;               Message "Reported to Reference10",1
      endif
              endif
    endif
            endif
  endif
        endif
    endif
End
end
 
Begin ScriptEffectFinish
begin ScriptEffectFinish
; if (NotReported == 1)
;   if (NotReported == 1)
;   return
;       return
; else
;   else
;I have never seen the following code execute.  It isn't necessary anyhow, but it was an attempt to directly
;; I have never seen the following code execute.  It isn't necessary anyhow, but it was an attempt to directly
;return the reference
;; return the reference
    MessageBox "Activating the EnemyFinder"
        MessageBox "Activating the EnemyFinder"
    EnemyFinderRef1.Activate self 1
        EnemyFinderRef1.Activate self 1
; endif
;   endif
End
end


Clearly I have some debug code in there you can uncomment etc. Now, you can see it references variables in an EnemyFinderRef1 that we don't know about. Well first, let's define the script that defines those variables.
Clearly I have some debug code in there you can uncomment etc. Now, you can see it references variables in an EnemyFinderRef1 that we don't know about. Well first, let's define the script that defines those variables.


CODE
scriptname EnemyFinder
 
scriptname EnemyFinder
ref AskingRef
 
short RefsRequested
ref AskingRef
ref reference1
short RefsRequested
ref reference2
ref reference1
ref reference3
ref reference2
ref reference4
ref reference3
ref reference5
ref reference4
ref reference6
ref reference5
ref reference7
ref reference6
ref reference8
ref reference7
ref reference9
ref reference8
ref reference10
ref reference9
ref reference10
short ref1full
 
short ref2full
short ref1full
short ref3full
short ref2full
short ref4full
short ref3full
short ref5full
short ref4full
short ref6full
short ref5full
short ref7full
short ref6full
short ref8full
short ref7full
short ref9full
short ref8full
short ref10full
short ref9full
short ref10full
ref temp
 
ref self
ref temp
ref self
short doonce
 
short doonce
Begin OnActivate
 
  if (doonce == 0)
begin OnActivate
    set self to EnemyFinderRef1
    if (doonce == 0)
    set AskingRef to GetActionRef
        set self to EnemyFinderRef1
    set doonce to 1
        set AskingRef to GetActionRef
  endif
        set doonce to 1
;The code until the sets is supposed to deal with the ScriptEffectFinish code
    endif
  set temp to GetActionRef
;;The code until the sets is supposed to deal with the ScriptEffectFinish code
  if (temp != AskingRef)
    set temp to GetActionRef
    if (temp != player)
    if (temp != AskingRef)
      AskingRef.Activate temp 1
        if (temp != player)
    endif
            AskingRef.Activate temp 1
  endif
        endif
  set ref1full to 0
    endif
  set ref2full to 0
    set ref1full to 0
  set ref3full to 0
    set ref2full to 0
  set ref4full to 0
    set ref3full to 0
  set ref5full to 0
    set ref4full to 0
  set ref6full to 0
    set ref5full to 0
  set ref7full to 0
    set ref6full to 0
  set ref8full to 0
    set ref7full to 0
  set ref9full to 0
    set ref8full to 0
  set ref10full to 0
    set ref9full to 0
  set RefsRequested to 1
    set ref10full to 0
  float xval
    set RefsRequested to 1
  float yval
    float xval
  float zval
    float yval
  self.moveto player, 0.0, 0.0, 100.0
    float zval
; set xval to (self.getpos x)
    self.moveto player, 0.0, 0.0, 100.0
; set yval to (self.getpos y)
;   set xval to (self.getpos x)
; set zval to (self.getpos z)
;   set yval to (self.getpos y)
; MessageBox "Moved to (%.2f, %.2f, %.2f)", xval, yval, zval
;   set zval to (self.getpos z)
  cast TargetDetection Player
;   MessageBox "Moved to (%.2f, %.2f, %.2f)", xval, yval, zval
End
    cast TargetDetection Player
end
 


Again I have some debug code there. Basically this is a script that will store the references and the checks to see if they are full. It goes on an object (an Activator is a great choice) and each time it is activated, it moves to roughly the actors location and casts the spell at the actor(it does no damage and isn't hostile, I just needed a target for it). Right now you can still hear the spell go off, but I didn't worry too much about that for this Proof of Concept (I named the spell TargetDetection remember?).
Again I have some debug code there. Basically this is a script that will store the references and the checks to see if they are full. It goes on an object (an Activator is a great choice) and each time it is activated, it moves to roughly the actors location and casts the spell at the actor(it does no damage and isn't hostile, I just needed a target for it). Right now you can still hear the spell go off, but I didn't worry too much about that for this Proof of Concept (I named the spell TargetDetection remember?).
Line 186: Line 184:
Now all that must be done is to Activate EnemyFinderRef1. I added a script to an Iron Bow to test it, but you could put it on anything, or you could make the EnemyFinderRef1 run in GameMode instead of on activate and go off every X seconds as you decide. I will include the script I have which is object agnostic (it isn't bow specific) and you can take the code and modify it as you see fit. I've included printouts that aren't perfect but work to the script code. You'll get the first two message boxes (if there are two nearby references) right now since I didn't bother to fix the MessageBox chain. I tried to print the reference values but that failed.
Now all that must be done is to Activate EnemyFinderRef1. I added a script to an Iron Bow to test it, but you could put it on anything, or you could make the EnemyFinderRef1 run in GameMode instead of on activate and go off every X seconds as you decide. I will include the script I have which is object agnostic (it isn't bow specific) and you can take the code and modify it as you see fit. I've included printouts that aren't perfect but work to the script code. You'll get the first two message boxes (if there are two nearby references) right now since I didn't bother to fix the MessageBox chain. I tried to print the reference values but that failed.


CODE
scriptname RangeTest
 
scriptname RangeTest
float timer
 
short doonce
float timer
short player_owned
short doonce
short player_owned
ref actorfinder
 
ref myself
ref actorfinder
ref myself
Begin OnActivate
 
  if (IsActionRef player == 1)
begin OnActivate
    set player_owned to 1
    if (IsActionRef player == 1)
    set actorfinder to enemyfinderref1
        set player_owned to 1
    set myself to this
        set actorfinder to enemyfinderref1
    Activate
        set myself to this
  else
        Activate
    long distance
    else
    ref actor
        long distance
    set actor to GetActionRef
        ref actor
    set distance to (GetDistance actor)
        set actor to GetActionRef
    MessageBox "I am %.0f distance from %.0f", distance, actor
        set distance to (GetDistance actor)
  endif
        MessageBox "I am %.0f distance from %.0f", distance, actor
  End
    endif
end
 
begin OnDrop
    set player_owned to 0
end
 
begin GameMode
    if (player_owned)
        if (doonce == 0)
            set timer to 10
            set doonce to 1
        endif
        if (timer > 0)
            set timer to timer - GetSecondsPassed
            long distance
            short button
            ref actor
            if (timer < 5)
                set EnemyFinderRef1.RefsRequested to 0
            endif
            if (EnemyFinderRef1.ref1full == 1)
                set actor to EnemyFinderRef1.reference1
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 1 %.0f", distance, actor
                set EnemyFinderRef1.ref1full to 0
            endif
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref2full == 1)
                set actor to EnemyFinderRef1.reference2
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 2 %.0f", distance, actor
                set EnemyFinderRef1.ref2full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref3full == 1)
                set actor to EnemyFinderRef1.reference3
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 3 %.0f", distance, actor
                set EnemyFinderRef1.ref3full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref4full == 1)
                set actor to EnemyFinderRef1.reference4
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 4 %.0f", distance, actor
                set EnemyFinderRef1.ref4full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref5full == 1)
                set actor to EnemyFinderRef1.reference5
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 5 %.0f", distance, actor
                set EnemyFinderRef1.ref5full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref6full == 1)
                set actor to EnemyFinderRef1.reference6
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 6 %.0f", distance, actor
                set EnemyFinderRef1.ref6full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref7full == 1)
                set actor to EnemyFinderRef1.reference7
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 7 %.0f", distance, actor
                set EnemyFinderRef1.ref7full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref8full == 1)
                set actor to EnemyFinderRef1.reference8
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 8 %.0f", distance, actor
                set EnemyFinderRef1.ref8full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref9full == 1)
                set actor to EnemyFinderRef1.reference9
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 9 %.0f", distance, actor
                set EnemyFinderRef1.ref9full to 0
            endif
            set button to -2
            set button to getbuttonpressed
            if (button > -1 && EnemyFinderRef1.ref10full == 1)
                set actor to EnemyFinderRef1.reference10
                set distance to (GetDistance actor)
                MessageBox "I am %.0f distance from Reference 10 %.0f", distance, actor
                set EnemyFinderRef1.ref10full to 0
            endif
        else           
            Message "Looking for Actor Range", 1
            actorfinder.Activate myself 1
            set timer to 10
        endif
    endif
end


Begin OnDrop
 
  set player_owned to 0
End
Begin GameMode
  if (player_owned)
    if (doonce == 0)
      set timer to 10
      set doonce to 1
    endif
    if (timer > 0)
      set timer to timer - GetSecondsPassed
      long distance
      short button
      ref actor
      if (timer < 5)
        set EnemyFinderRef1.RefsRequested to 0
      endif
      if (EnemyFinderRef1.ref1full == 1)
        set actor to EnemyFinderRef1.reference1
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 1 %.0f", distance, actor
        set EnemyFinderRef1.ref1full to 0
      endif
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref2full == 1)
        set actor to EnemyFinderRef1.reference2
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 2 %.0f", distance, actor
        set EnemyFinderRef1.ref2full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref3full == 1)
        set actor to EnemyFinderRef1.reference3
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 3 %.0f", distance, actor
        set EnemyFinderRef1.ref3full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref4full == 1)
        set actor to EnemyFinderRef1.reference4
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 4 %.0f", distance, actor
        set EnemyFinderRef1.ref4full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref5full == 1)
        set actor to EnemyFinderRef1.reference5
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 5 %.0f", distance, actor
        set EnemyFinderRef1.ref5full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref6full == 1)
        set actor to EnemyFinderRef1.reference6
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 6 %.0f", distance, actor
        set EnemyFinderRef1.ref6full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref7full == 1)
        set actor to EnemyFinderRef1.reference7
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 7 %.0f", distance, actor
        set EnemyFinderRef1.ref7full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref8full == 1)
        set actor to EnemyFinderRef1.reference8
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 8 %.0f", distance, actor
        set EnemyFinderRef1.ref8full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref9full == 1)
        set actor to EnemyFinderRef1.reference9
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 9 %.0f", distance, actor
        set EnemyFinderRef1.ref9full to 0
      endif
      set button to -2
      set button to getbuttonpressed
      if (button > -1 && EnemyFinderRef1.ref10full == 1)
        set actor to EnemyFinderRef1.reference10
        set distance to (GetDistance actor)
        MessageBox "I am %.0f distance from Reference 10 %.0f", distance, actor
        set EnemyFinderRef1.ref10full to 0
      endif
    else           
      Message "Looking for Actor Range", 1
      actorfinder.Activate  myself 1
      set timer to 10
    endif
  endif
End


Clearly you could make your timeout value a global or set it to something different based on the situation. Also you want to pull the references out from your script as soon as possible so that you can make sure you don't miss the one you want due to a one not being able to report in time because the registers are full.
Clearly you could make your timeout value a global or set it to something different based on the situation. Also you want to pull the references out from your script as soon as possible so that you can make sure you don't miss the one you want due to a one not being able to report in time because the registers are full.