Home   Help Search Login Register  

Author Topic: Question about EH and Scripts  (Read 3628 times)

0 Members and 1 Guest are viewing this topic.

Offline Bingoz

  • Members
  • *
Question about EH and Scripts
« on: 25 Feb 2011, 20:48:41 »
I am trying to understand the best way of passing EH data to scripts.

A question first, what is the better way of detecting if shots are fired at a specific unit?

I was trying something like this.

Code: [Select]
wepFired = this AddEventHandler ["Fired", {this exec "Fired.sqf"}];

Fired.sqf ( Fictional at the moment )
Code: [Select]

UnitDat = _this;

_Unit = UnitDat select 0;
_Weap = UnitDat select 1;
_WAmo = UnitDat select 3;

// -----------------------------------------------------------------  Get Position of Shooter ---------
_UnitPos = Position _Unit;
_UnitPosx = _UnitPos select 0;
_UnitPosy = _UnitPos select 1;

// -----------------------------------------------------------------  Get Shooters Target, Shooters Range, and Skill  -------------
_UnitTar = GetTarget _Unit;
_UnitRng = ( _Unit GetDistance  _UnitTar );
_UnitSkl = GetSkill _Unit;

// ----------------------------------------------------------------- Determine if under fire ------------------------------
if (_UnitTar == Gn1) then { isUndFir = True } Else { isUndFir = False};

Hint str _WAmo;

« Last Edit: 25 Feb 2011, 21:54:39 by Bingoz »

Offline Wolfrug

  • Addons Depot
  • Former Staff
  • ****
  • Official OFPEC Old Timer
Re: Question about EH and Scripts
« Reply #1 on: 26 Feb 2011, 17:34:25 »
Hi!

A much, much easier way of doing this would be to simply use the FiredNear eventhandler on the target instead. That way no-one but the one you need would have to have an eventhandler attached, and...yeah. Note that it runs whenever the unit fires as well, so be sure to exit the script if _unit == _unit :)

An example script would be something like:

g1 addeventhandler ["FiredNear", {_this execvm "underfire.sqf"}];

Code: [Select]
_unit = _this select 0;
_firer = _this select 1;

if (_unit == _firer) exitWith {};

_dist = _this select 2;
_weapon = _this select 3;

The eventhandler gives you everything you need by itself. :) Good luck!

Wolfrug out.
"When 900 years YOU reach, look as good you will not!"

Offline Bingoz

  • Members
  • *
Re: Question about EH and Scripts
« Reply #2 on: 02 Mar 2011, 03:33:46 »
Quote
_unit = _this select 0;
_firer = _this select 1;

if (_unit == _firer) exitWith {};

Roger that, I was trying something like that, and I am noticing that Even thought I am using a ExitWith {}; that the code that follows is still ran, any way of killing the script at that point?

Offline i0n0s

  • Moderator
  • *****
Re: Question about EH and Scripts
« Reply #3 on: 02 Mar 2011, 10:44:14 »
exitWith shouldn't be used to exit scripts. Take the other way and use a normal if.

Offline h-

  • OFPEC Site
  • Administrator
  • *****
  • Formerly HateR_Kint
    • OFPEC
Re: Question about EH and Scripts
« Reply #4 on: 02 Mar 2011, 15:48:29 »
Quote
exitWith shouldn't be used to exit scripts
Out of curiosity, why?
Has always worked for me...  :dunno:
Project MCAR   ---   Northern Fronts   ---   Emitter 3Ditor
INFORMATIVE THREAD TITLES PLEASE. "PLEASE HELP" IS NOT ONE..
Chuck Norris can divide by zero.

Offline Wolfrug

  • Addons Depot
  • Former Staff
  • ****
  • Official OFPEC Old Timer
Re: Question about EH and Scripts
« Reply #5 on: 02 Mar 2011, 19:42:47 »
In this case I added that exitWith because apparently this eventhandler is run even when the unit itself is doing the shooting: this basically just checks if the unit == the firer and if so -> quit.

The only reason exitWith wouldn't work here is because you're running the code inside a scope, rather than in the main scope. Let me explain:

Code: [Select]
// this is your main scope
_stuff = _this select 0;

for "_i" from 0 to 5 do
{
//this is a secondary scope
if (_i == 4) exitWith {};
};

//the above exitwith only exited out of the secondary scope and back to the main one, NOT the whole script, thus the below code still runs

hint str (_stuff);

// exit from main scope
if (true) exitwith {hint "Weee!"};

// this code is never run
hint "Booo!";

Get it? So make sure you're not messing up with the scopes, and the exitwith should work just fine. :)

Wolfrug out.
"When 900 years YOU reach, look as good you will not!"

Offline i0n0s

  • Moderator
  • *****
Re: Question about EH and Scripts
« Reply #6 on: 02 Mar 2011, 19:58:24 »
@h-
Quote
When you use exitWith not inside a loops, the behaviour is undefined - sometimes it may exit the script, sometimes some other scope, but this is not intended and designed behaviour of this command, and it is not guaranteed to work reliably.

It exits the loop only, not the script.
Written by Suma

Offline Bingoz

  • Members
  • *
Re: Question about EH and Scripts
« Reply #7 on: 02 Mar 2011, 21:25:14 »
okay all of this is correct, as in fact ExitWith in any scope other than the main scope is useless if you are trying to kill the script all to gather.

So the real question would be, HOW can one Exit a script no matter what scope it is in, or alternatively is there a way to us something like a GOTO,?

Example of the old Gotos I am use to.

Code: [Select]
If a = A then Goto "Spaming!"

end if

"Spaming!"
Runs code here, bypassing code after the if, IF a  = a, Else it runs the code following the if.

Offline i0n0s

  • Moderator
  • *****
Re: Question about EH and Scripts
« Reply #8 on: 03 Mar 2011, 01:14:29 »
If a != A then
... code after the if
end if
"Spaming!"
Runs code here, bypassing code after the if, IF a  = a, Else it runs the code following the if.

Offline h-

  • OFPEC Site
  • Administrator
  • *****
  • Formerly HateR_Kint
    • OFPEC
Re: Question about EH and Scripts
« Reply #9 on: 03 Mar 2011, 14:02:12 »
Written by Suma
Well, despite that I have never ever experienced any problems exiting scripts using exitWith..

EDIT:
Oh, and recently discovered another "sqs-esque" way of exiting sqf scripts; using breakTo with a non-existent scope (as in not set with scopeName), like breakTo "blah". Terminates the whole script, not just the scope it's "run" in.

Code: [Select]
private["_i"];

_i = 0;
while {true} do {
player sideChat "runs";
sleep 1;
_i = _i + 1;
if (_i>= 3) then {breakTo "blah"};
};

hintC "exited";
The hintC won't show.
Discovered this in ArmA (by accident), seems to work at least in Arma2 1.08/OA 1.57..
« Last Edit: 03 Mar 2011, 15:44:01 by h- »
Project MCAR   ---   Northern Fronts   ---   Emitter 3Ditor
INFORMATIVE THREAD TITLES PLEASE. "PLEASE HELP" IS NOT ONE..
Chuck Norris can divide by zero.

Offline Bingoz

  • Members
  • *
Re: Question about EH and Scripts
« Reply #10 on: 04 Mar 2011, 23:28:43 »
Quote
Code: [Select]
private["_i"];

_i = 0;
while {true} do {
player sideChat "runs";
sleep 1;
_i = _i + 1;
if (_i>= 3) then {breakTo "blah"};
};

hintC "exited";

Yes your on the same path I am, I was just looking at the Breakto. I will give it a try and let ya know if it worked as needed.

Thanks guys I truly appreciate your efforts of answering this questions.

Offline haroon1992

  • Members
  • *
  • My life is hopeless...
Re: Question about EH and Scripts
« Reply #11 on: 11 Mar 2011, 09:44:39 »
Thanks for everyone, this thread explains many of the mysterious problems with exiting scripts in ArmA 2.
I'm gonna fix up all those errors in my scripts.


But I have a little confusion with what Suma said.

Quote
When you use exitWith not inside a loops, the behaviour is undefined - sometimes it may exit the script, sometimes some other scope, but this is not intended and designed behaviour of this command, and it is not guaranteed to work reliably.

Does this mean that exitWith is not reliable to exit scripts? Does it mean it only works SOMETIMES?

Sorry, I'm too dumb to understand the experts' conversation. :(

Regards,
Haroon1992
Very busy with life, business, and other stuff. Away from OFP for months. Not sure if I could get back onto it. :(

Offline JamesF1

  • Editors Depot Staff
  • *****
    • JamesBurgess.co.uk
Re: Question about EH and Scripts
« Reply #12 on: 11 Mar 2011, 12:05:09 »
Fundamentally it means that the behaviour is undefined - as in, it could change at any time, be affected by an update to the lexer/parser, or anything like that.  In the most straightforward way possible: BIS didn't 'intend' it to function like that... so it could change easily, and without notice, in the future :)

That doesn't mean it doesn't work now it just means that it's not guaranteed to remain that way.  And, there could be circumstances under which it doesn't work already.

Offline Denisko-Redisko

  • Members
  • *
Re: Question about EH and Scripts
« Reply #13 on: 24 Mar 2011, 19:40:55 »
Quote
Fundamentally it means that the behaviour is undefined
???

From http://www.arma2.com/comref/comref.html
Code: [Select]
if exitWith code

Operand types:
    if: If Type
    code: Code
Compatibility:
    Version 2 required.
Type of returned value:
    Any
Description:
    if result of condition is true, evaluates code, and __current block__ with result of code

Example:
    if (_x>5) exitWith {echo "_x is too big";_x} , result is [when _x is greater then 5, outputs message and terminates code in current level with value of _x
I emphasized "current block". This command terminates the current block.
for example:
Code: [Select]
_searchedValue = ({
    if (_k == _x select 0) exitwith { _x select 1 };
    _defaultValue;
} foreach [[key1, value1], [key2, value2], ... ])

sorry for my english

Offline JamesF1

  • Editors Depot Staff
  • *****
    • JamesBurgess.co.uk
Re: Question about EH and Scripts
« Reply #14 on: 25 Mar 2011, 00:46:11 »
Interesting - I was merely referencing Suma's comment about it being undefined when used outside of a loop... but then your reference would seem to counter that, anyway.  I wonder what the 'official' line is, these days (in truth, I'd probably suggest the ComRef is the more accurate reference).  :dunno:

Offline Denisko-Redisko

  • Members
  • *
Re: Question about EH and Scripts
« Reply #15 on: 25 Mar 2011, 08:14:18 »
Quote
Interesting - I was merely referencing Suma's comment about it being undefined when used outside of a loop... but then your reference would seem to counter that, anyway.
Oh, sorry   :confused:
but nevertheless:
Code: [Select]
_var = _k call {
    if (_this == 1) exitwith { "a" };
    if (_this == 2) exitwith { "b" };
    if (_this == 3) exitwith { "c" };
    "d" // default value
}
« Last Edit: 25 Mar 2011, 08:16:16 by Denisko-Redisko »
sorry for my english