Keep getting 'Cannot Evaluate Sub' Errors

Posted by Sleaker on Thu 19 Sep 2002 03:22 AM — 7 posts, 22,927 views.

#0
I have a Sub like this
Sub OnClaimTower2(thename, theoutput, theparameters)
If Trim(theparameters(2)) = "Monolith Chemicals" And World.GetVariable("MonolithUnderAttack") = "TRUE" Then
World.SetVariable "MonolithUnderAttack", "FALSE"
World.SetVariable "MonolithEndTime", Timer
World.SetVariable "MonolithSeconds", World.GetVariable("MonolithEndTime") - World.GetVariable("MonolithStartTime")
World.SetVariable "MonolithMinutes", Fix((World.GetVariable("MonolithEndTime") - World.GetVariable("MonolithStartTime"))/60)
World.SetVariable "MonolithSeconds", FormatNumber(World.GetVariable("MonolithSeconds") - (World.GetVariable("MonolithMinutes")*60),2)
If World.GetVariable("MonolithSeconds") < "0" Then
World.SetVariable "MonolithSeconds", World.GetVariable("MonolithSeconds") + (24*3600)
End If
World.send World.GetVariable("TowerSendMethod") & " It took " & World.GetVariable("MonolithMinutes") & " minutes " & World.GetVariable("MonolithSeconds") & " seconds for " & Trim(theparameters(1)) & " to claim Monolith Chemicals"

End Sub
With many more copies of that with different ifs etc.
and I have a trigger like this:

[EconProduction] * has claimed *.
Sequence: 100
Label: LblOnClaimTower2
Script: OnClaimTower2


am I doing something wrong or should I be doing it differently?
Australia Forum Administrator #1
It looks a bit complicated. Try something like this:


Sub OnClaimTower2(thename, theoutput, theparameters)
dim totalsecs, mins, secs

  If Trim(theparameters(2)) = "Monolith Chemicals" AND _
     World.GetVariable("MonolithUnderAttack") = "TRUE" Then
      World.SetVariable "MonolithUnderAttack", "FALSE"

'
'  calculate how long it took
'
  totalsecs = datediff ("s", GetVariable("MonolithStartTime"), Now)
  mins = totalsecs / 60
  secs = totalsecs mod 60 ' get remainder
  World.send World.GetVariable("TowerSendMethod") & _
     " It took " & mins & " minutes " & _    
     secs & " seconds for " & Trim(theparameters(1)) & _
     " to claim Monolith Chemicals"

End If


End Sub



I haven't tested it, but I think it would do the job.

Also, I wouldn't have heaps of copies of that, just do something like a CASE statement at the start that translates "Monolith Chemicals" into "Monolith" (or whatever) and use that inside the rest of the sub.

eg.


totalsecs = datediff ("s", GetVariable(TargetName & "StartTime"), Now)
Amended on Thu 19 Sep 2002 05:24 AM by Nick Gammon
#2
Well, see, the reason why I'm using world.setvariables is because there are about 12 of these towers that I am logging. and I need t olog each one independantly, that's why so many copies of that statement and why I'm not using Dims. but why would it be telling me it can't run the Sub when some of them work and some of them don't and they are all set up exactly the same.
USA #3
It is still possible to use one sub, but one comment.. If you are loging 12 different towers don't you also need 12 different sets of variables? Otherwise all of them are using the same data and interfere with each other. The following uses different variables for each tower in a case statement, so each should log individually. You still have to change whatever sets MonolithUnderAttack to "TRUE", so that it uses Mon1UnderAttack, Mon2UnderAttack, Mon3UnderAttack, etc., but that can probably also be handled using a similar case statement and single sub.


sub OnClaimTower(thename, theoutput, theparameters)
  dim totalsecs, mins, secs
  dim ParaTest = Trim(theparameters(2))
  dim MonName, MonAtt, MonTime
  select case thename
    case "LblOnClaimTower1"
      MonName = "Mon1" 'So we can use the same if then for all.
      MonAtt = world.getvariable("Mon1UnderAttack")
      MonTime = world.getvariable("Mon1StartTime")
    case "LblOnClaimTower2"
      MonName = "Mon2"
      MonAtt = world.getvariable("Mon2UnderAttack")
      MonTime = world.getvariable("Mon2StartTime")
    ' Add the rest here.
  end select
  If ParaTest = "Monolith Chemicals" AND MonAtt = "TRUE" then
    World.SetVariable MonName & "UnderAttack", "FALSE"

    '
    '  calculate how long it took
    '
    totalsecs = datediff ("s", MonTime, Now)
    mins = totalsecs / 60
    secs = totalsecs mod 60 ' get remainder
    World.send World.GetVariable("TowerSendMethod") & _
     " It took " & mins & " minutes " & _   
     secs & " seconds for " & Trim(theparameters(1)) & _
     " to claim Monolith Chemicals"
  End If
End Sub

Just make all your triggers call OnClaimTower, instead of the individual ones you where using. As with Nick's version this has not been tested, but should work. ;)
Australia Forum Administrator #4
Quote:

Well, see, the reason why I'm using world.setvariables is because there are about 12 of these towers that I am logging. and I need t olog each one independantly, that's why so many copies of that statement and why I'm not using Dims.


My suggested improvement actually retained different variable names, so that would still work. Notice the use of:


totalsecs = datediff ("s", GetVariable(TargetName & "StartTime"), Now)


In that example line the GetVariable gets a variable which is the TargetName concatenated with the words "StartTime".
USA #5
Oops.. I hand't looked at the stuff at the bottom real hard, just at the main chunk of code. Looks like I am developing your 'skimming' disease Nick. lol

I was also considering, however the possibility that more than on tower could be under attack at once. I suppose I don't really get the whole thing. It looks like it goes:

Attacking - Set UnderAttack to false
Success - Set UnderAttack to true, then display time.

This is really odd, but 'if' more than one can be under attack at a given time, then changing that value will mess up which ever one is not currently displaying the time. I was a little unclear about what was actually happening.
Australia Forum Administrator #6
Quote:

Looks like I am developing your 'skimming' disease Nick. lol


It's quite difficult to cure, I believe. ;)