Jump to content
johnnyboy

detect when ai unit aiming weapon at other ai unit

Recommended Posts

I want to detect when ai unit is pointing his weapon at another ai unit.  So I think I need to ray cast from weapon using weapon direction.  I came up with this based on Killzone Kid's Bob example:

 _unit = dude1; 
 _beg = eyePos _unit; 
 _endW = (_beg vectorAdd (_unit weaponDirection currentWeapon _unit vectorMultiply 15)); 
 objs = lineIntersectsWith [_beg, _endW]; 

When I test this, I have player stand directly in front of dude1 unit (and dude1 has his rifle raised and pointing at me), but player is never in the objs array.  I do see plant and building objects in the objs array, but not the player object.  What am I doing wrong?

 

Is there a better way to return human object an ai is pointing his weapon at?

  • Like 1

Share this post


Link to post
Share on other sites

Hi johnnyboy,

 

I have a script in this regard on my hard drive (which i made for a project of mine). Currently i have no acces to my computer, but I will poste my code snipped later during the day.

  • Thanks 1

Share this post


Link to post
Share on other sites
Just now, wogz187 said:

@johnnyboy,
If you see the return array no problem maybe just this instead?
lineIntersectsObjs

Thanks for the reply.  I tried all the different intersects commands, and none of them were returning object of type "Man" though.  

Share this post


Link to post
Share on other sites

Hi johnnyboy,

 

this is what I use:

 

Spoiler

 

//params ["_BAG_Unit","_BAG_Target"];

// {

_BAG_ICON =  "a3\ui_f\data\IGUI\RscIngameUI\RscOptics\turretIndicatorObsTurret2.paa";
_deviation = 0;


    _BAG_ICON_COLOR = [0.8,0,0,0.4];
    _BAG_Target = _x;
    _BAG_boolean = false;

    if (alive _BAG_Target) then {
    
        if (!alive _BAG_Unit || {weaponLowered _BAG_Unit}) exitWith {_BAG_boolean};
        
        _BAG_pos0 = getPosASL _BAG_Unit;
        
        _BAG_pos1 =  unitAimPositionVisual _BAG_Target;
        
        _BAG_wpn = currentWeapon _BAG_Unit;
        
        _BAG_wdir = _BAG_Unit weaponDirection _BAG_wpn;
        
        _BAG_dst = _BAG_pos0 distance2D _BAG_pos1;
        
        _BAG_pos2 = [(_BAG_pos0 select 0) + _BAG_dst * (_BAG_wdir select 0), (_BAG_pos0 select 1) + _BAG_dst * (_BAG_wdir select 1), (_BAG_pos0 select 2) + _BAG_dst * (_BAG_wdir select 2)];
        
        _deviation = _BAG_pos2 distance2D _BAG_pos1;
        
        _BAG_CV = ([objNull, "VIEW"] checkVisibility [eyePos _BAG_Unit,AGLToASL unitAimPositionVisual _BAG_Target]);
        
        if (_BAG_CV  >= 0.5 && {_deviation < 5}) then {_BAG_boolean = true; _BAG_ICON_COLOR = [1,0,0,1]; _BAG_Unit setVariable ["BAG_t_i_sight",true];};
        
        _BAG_TEXT =  format ["%1",(_forEachindex + 1)];
    
        //drawIcon3D [_BAG_ICON,_BAG_ICON_COLOR,(visiblePosition _x) vectorAdd [0,0,4],4,4,0,_BAG_TEXT,0.5,0.04, "PuristaSemibold"];
        
        if ((!_BAG_boolean) && {_BAG_Unit getVariable "BAG_t_i_sight"}) then {_BAG_Unit setVariable ["BAG_t_i_sight",nil];};    
        
    };       

 

// } forEach ......        

 

 

I use it in an oneachFrame eventhandler, but you can use it in a while loop or whatever.

Basic Idea or source of this script, is actually not mine. Found in some forum threat.

  • Thanks 1

Share this post


Link to post
Share on other sites
4 minutes ago, gizz46 said:

Hi johnnyboy,

 

this is what I use:

Thanks Gizz, I'll try it out when I go into Arma later.  But it may not work for me because, I think this test...

 

4 minutes ago, gizz46 said:

_BAG_CV = ([objNull, "VIEW"] checkVisibility [eyePos _BAG_Unit,AGLToASL unitAimPositionVisual _BAG_Target]);

...is checking if eyepos shooter can see aimpos of target (if I understand this code correctly).  What I want to know is if the weapon is pointing directly at the target.  Example:  Shooter is standing, and target is prone 5 meters away.  If shooter is facing the target, and 2D weapon direction is toward target, that is not good enough, because weapon may be pointing above the prone target.  What I need to know is if weapon is pointing down exactly at target (so if shooter was to shoot, they would hit the target).

Share this post


Link to post
Share on other sites

Hey, just found this:

 

https://community.bistudio.com/wiki/weaponDirection (Example 2)

Draw AI eye direction (green) and weapon direction (red) in 3D:

bob = createGroup east createUnit ["O_Soldier_F", [0,0,0], [], 0, "NONE"];
bob setVehiclePosition [player modelToWorld [0,100,0], [], 0, "NONE"];
onEachFrame
{
	_beg = ASLToAGL eyePos bob;
	_endE = (_beg vectorAdd (eyeDirection bob vectorMultiply 100));
	drawLine3D [ _beg, _endE, [0,1,0,1]];
	_endW = (_beg vectorAdd (bob weaponDirection currentWeapon bob vectorMultiply 100));
	drawLine3D [_beg, _endW, [1,0,0,1]];
};

Give it a try.

(Can you get intersection from drawLine3D? 🤨).

  • Like 2

Share this post


Link to post
Share on other sites
2 minutes ago, RCA3 said:

Hey, just found this:

 

https://community.bistudio.com/wiki/weaponDirection (Example 2)

Draw AI eye direction (green) and weapon direction (red) in 3D:

Thanks RCA3.  That KillZone Kid example is what I based my experiments on.  If you run that code you see the weapon line drawn which is exactly what I want to use to see if it intersects an AI unit.  Unfortunately when I use this technique with any of the intersects commands, I can't get them to return the AI man object in the array of intersected objects.

 

I'm probably doing something wrong, but can't figure it out.  😖

  • Like 2

Share this post


Link to post
Share on other sites
29 minutes ago, johnnyboy said:

Thanks Gizz, I'll try it out when I go into Arma later.  But it may not work for me because, I think this test...

 

...is checking if eyepos shooter can see aimpos of target (if I understand this code correctly).  What I want to know is if the weapon is pointing directly at the target.  Example:  Shooter is standing, and target is prone 5 meters away.  If shooter is facing the target, and 2D weapon direction is toward target, that is not good enough, because weapon may be pointing above the prone target.  What I need to know is if weapon is pointing down exactly at target (so if shooter was to shoot, they would hit the target).

 

this is what the variable  -  _deviation = _BAG_pos2 distance2D _BAG_pos1 - is for. you can leave _BAG_CV out of the check if you want to...

  • Thanks 1

Share this post


Link to post
Share on other sites

@johnnyboy,

Quote

Thanks for the reply.  I tried all the different intersects commands, and none of them were returning object of type "Man" though.  


It's like units are a black void for this function. Weird. You would think that's the primary purpose.

I made example one a toggle-able function for testing,
 

Spoiler

you_fnc_TargetInfo=
{	params ["_doStart"];
	if (_doStart==1) then {
		Sto = []; 
		Fn = {	{ Sto set
	[_foreachindex,lineIntersectsObjs [(eyePos player),(ATLtoASL screenToWorld [0.5,0.5]),objNull,objNull,false,_x]]; 
		} forEach [1,2,4,8,16,32]; 
  hintSilent format ["ALL_OBJECTS: %6", Sto select 0,Sto select 1,Sto select 2,Sto select 3,Sto select 4,Sto select 5];
		};
["Object_Checker","onEachFrame","Fn"] call BIS_fnc_addStackedEventHandler;
	};
	if (_doStart==0) then {
		["Object_Checker","onEachFrame","Fn"] call BIS_fnc_removeStackedEventHandler;
hint "";
		};
};

//call with: [1] call you_fnc_targetInfo; [0] call you_fnc_targetInfo;

 

 

  • Like 1
  • Thanks 1

Share this post


Link to post
Share on other sites
1 minute ago, wogz187 said:

It's like units are a black void for this function. Weird. You would think that's the primary purpose.

Maybe I'm not crazy after all and its not just me!

2 minutes ago, wogz187 said:

I made example one a toggle-able function for testing,

Thanks for the slick test function.

  • Like 1

Share this post


Link to post
Share on other sites
onEachFrame
{
    _beg = ASLToAGL eyePos player;
    _endE = (_beg vectorAdd (eyeDirection player vectorMultiply 100));
    drawLine3D [ _beg, _endE, [0,1,0,1]];
    _endW = (_beg vectorAdd (player weaponDirection currentWeapon player vectorMultiply 100));
    drawLine3D [_beg, _endW, [1,0,0,1]];
    hint str (((lineIntersectsSurfaces [AGLtoASL _beg, AGLtoASL _endW, player]) select 0) select 2);
};

AI gives results too, but their aim is too erratic so only every other frame is positive. 👍

  • Thanks 3

Share this post


Link to post
Share on other sites

@johnnyboy,

I adapted the function for @RCA3's script since it actually returns the info we wanted in the first place.

Spoiler

you_fnc_TargetInfo=
{	params [["_caller", player], ["_doStart", 0]];
objChecker=_caller;
if (_doStart==1) exitWith {
objectChecker = addMissionEventHandler ["EachFrame", {
		_beg = ASLToAGL eyePos objChecker;
    		_endE = (_beg vectorAdd (eyeDirection objChecker vectorMultiply 100));
    		drawLine3D [ _beg, _endE, [0,1,0,1]];
    		_endW = (_beg vectorAdd (objChecker weaponDirection currentWeapon objChecker vectorMultiply 100));
    		drawLine3D [_beg, _endW, [1,0,0,1]];
		hint str (((lineIntersectsSurfaces [AGLtoASL _beg, AGLtoASL _endW, objChecker]) select 0) select 2);
		}];
	};
if (_doStart==0) exitWith {removeMissionEventHandler ["eachFrame", objectChecker]; hint "";};
};

//call with: [player, 1] call you_fnc_targetInfo; [player, 0] call you_fnc_targetInfo;

 

Have fun!

  • Like 1
  • Thanks 2

Share this post


Link to post
Share on other sites

will cursorObject not be enough for player vs ai checking? Like:

Spoiler

 


playerAimingAt_fnc = {

params ["_aimingPlayer"];

if !(currentWeapon _aimingPlayer isEqualTo "") exitWith {hint "Cannot point a weapon if _aimingUnit is not armed!";};

private _playerTarget = objNull;

private _unitAimedAtInfo = objNull;

_playerTarget = cursorObject _aimingPlayer;

if !(isNull objectParent _playerTarget) exitWith {hint "targets not on foot so cannot be considered to being aimed at"; _unitAimedAtInfo};
if !(alive _playerTarget) exitWith {hint "pointing at dead bodies is useless"; _unitAimedAtInfo};
if (side group _aimingPlayer isEqualTo side group _playerTarget) exitWith {hint "we only care if the weapon is pointed at enemies"; _unitAimedAtInfo};

_unitAimedAtInfo = _playerTarget;
_unitAimedAtInfo 

};

 

 

 

 

for Ai vs. Ai or Ai vs. Player checking how about using the assignedTarget command?

Spoiler

 


aiAimingAt_fnc = {

params ["_aimingUnit"];

if !(currentWeapon _aimingUnit isEqualTo "") exitWith {hint "Cannot point a weapon if _aimingUnit is not armed!";};

private _aTarget = objNull;

private _unitAimedAtInfo = objNull;

_aTarget = assignedTarget _aimingUnit;

if !(isNull objectParent _aTarget) exitWith {hint "targets not on foot so cannot be considered to being aimed at"; _unitAimedAtInfo};
if !(alive_aTarget) exitWith {hint "pointing at dead bodies is useless"; _unitAimedAtInfo};
if (side group _aimingUnit isEqualTo side group _aTarget) exitWith {hint "we only care if the weapon is pointed at enemies"; _unitAimedAtInfo};

_unitAimedAtInfo = _aTarget;
_unitAimedAtInfo

};

 

 

 

assignedTarget will not be extremely precise but works well for Ai vs Ai and Ai vs Player checking as long as they are enemies to each other.

I don't think the command works on friendlies pointing guns at friendlies and also it probably only works when in combat but I don't see a situation where an Ai would point its gun at a friendly unit anyway nor a situation where an enemy would be pointing at an enemy and not in combat unless it is a scripted scene or something.

 

The second function also works for Ai vs Player checking (I think this is what this post is about), as long as you add a condition like: If (isPlayer _aTarget) then {_playerAimedAtInfo = _aTarget; _playerAimedAtInfo};

 

PS: Even thou not as precise and having its limitations, this method is far more performance friendly than an EachFrame Mission EH.

  • Like 2

Share this post


Link to post
Share on other sites

@LSValmont,

Quote

 "... this method is far more performance friendly than an EachFrame Mission EH."

I got sidetracked making a name checker tool. It wasn't really a solution to the topic.

cursorTarget totally works for (only) player.
Like you said, assignedTarget has some limitations.

 

Have fun!

  • Like 1

Share this post


Link to post
Share on other sites
2 hours ago, LSValmont said:

I don't think the command works on friendlies pointing guns at friendlies and also it probably only works when in combat but I don't see a situation where an Ai would point its gun at a friendly unit anyway nor a situation where an enemy would be pointing at an enemy and not in combat unless it is a scripted scene or something.

 

 

 

 I like it for both the immersion and tactical penalty of your AI having weapons at a ready when running thru a heavy civvie population. For instance, I penalize the player for always keepin his gun up, if he runs too close to Civs they yell out and attract attention of enemy soldiers. This makes you think about keeping your weapon in the ready position too much. With the above I can now apply to the players Ai squad who may be forced to be in a less 'ready position' in heavily populated areas. Thats just the way i like to roll doe.

  • Like 2

Share this post


Link to post
Share on other sites
1 hour ago, froggyluv said:

For instance, I penalize the player for always keepin his gun up, if he runs too close to Civs they yell out and attract attention of enemy soldiers. This makes you think about keeping your weapon in the ready position too much.

Totally agree.  Pointing your weapon in friendlies and civ's faces without a reaction is an immersion breaker and deserves punishment.

  • Like 1

Share this post


Link to post
Share on other sites
12 hours ago, Larrow said:

Bob and Bill

Thanks Larrow.  That works well.  I greatly apperciate the slick example.   Its funny how Bob can rotate past pointing at Bill sometimes without it registering...very delicate.

 

Here's Larrow's code for those of you who don't want to download his sample mission:

addMissionEventHandler[ "Draw3D", { 
 _target = objNull; 
 _beg = ASLToAGL eyePos bob; 
 _endE = (_beg vectorAdd (eyeDirection bob vectorMultiply 100)); 
 drawLine3D [ _beg, _endE, [0,1,0,1]]; 
 _endW = (_beg vectorAdd (bob weaponDirection currentWeapon bob vectorMultiply 100)); 
 drawLine3D [_beg, _endW, [1,0,0,1]]; 
 if ( lineIntersectsSurfaces[ AGLToASL _beg, AGLToASL _endw, bob, objNull, true ] 
	findIf{ if ( _x #2 isKindOf "Man" ) then { _target = _x #2; true }else{ false } } > -1 ) then 
 { 
  systemChat format[ "%1: Bob is aming at %2", time, _target ]; 
 }; 
}]; 
 
player addAction[ "Bob target Bill", { 
 bob commandTarget bill; 
}];

 

  • Like 2

Share this post


Link to post
Share on other sites

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now

×