Jump to content
Sign in to follow this  
froggyluv

Getting All Civilians to Talk

Recommended Posts

 Tried writing 1st function:

fnc_Civ = {
_x = _this select 0;
_sounds = [["banter1"],["banter2"],["banter3"],["banter4"],["banter5"],["banter6"]] Bis_Fnc_selectRandom;

if (side _x == civilian) AND (_x distance units group player < 5) then { _x say3d _sounds
        
    
} foreach allUnits;

 };
 

Calling it from a Trigger that is attached to Player which also has a 5m radius with Civilians Present and Repeatedly but cant get the function to fire. I'd like for all Civilians including those spawned by DAC to speak as well  -any help appreciated :)

Share this post


Link to post
Share on other sites

Try this,

init.sqf:

call compile preprocessFile "myscript.sqf";
[] spawn fnc_civ;

myscript.sqf:

fnc_Civ = {

_radius = 500;
_unit = nearestObjects [player, ["CAManBase"], _radius];

_sounds = ["banter1", "banter2", "banter3", "banter4", "banter5", "banter6"];

_play_sound = _sounds call BIS_fnc_SelectRandom;

if (side _unit == civilian) && ((_unit distance player) < 5) then {

{_x say3D _play_sound } foreach _unit;

 };

Share this post


Link to post
Share on other sites

Calling it from a Trigger that is attached to Player...

I'm not sure I'd use a trigger - whoes condition gets executed/checked every frame - for such a thing. Why not spawn a simple FSM (or just a script with a while-true-loop), and then check with nearestObjects using a slightly larger radius maybe, but also a longer delay to recheck again (maybe every 3-10 seconds).

Also make sure to randomize the (start-)time of the say3d commands a bit, either by sleeping for some time between multiple calls (using a queue), or you could also spawn a new thread for each unit with randomized sleep before saying something.

And then you might wanna mark units that sayed something (the last time), to have a cooldown per unit. Maybe even filter randomly, s.t. only every nth unit will say something (just in case things are too much, or too robotic/predictable).

 

Other than that, I have no idea why your trigger doesn't seem to be working.

Oh, and: in your script above you seem to be picking a sound at random only once(!), then that sound will be used for allUnits (well, this turn/cycle. I guess multiple civilians could end up there at the same time...). I don't think that's what you really want. Randomly picking an element out of an array is cheap, so maybe put it inside the foreach loop. ;)

 

Hm, why are you using allUnits anyways? Shouldn't the trigger give you a list (thisList) including the units that triggered the thing? That should do it already.

Share this post


Link to post
Share on other sites

 Not working Ranwer -its firing but no sounds.

 

civBanter.sqf
 

fnc_Civ = {

_radius = 500;
_unit = nearestObjects [player, ["CAManBase"], _radius];

Hintc "Im working!!";

_sounds = ["banter1", "banter2", "banter3", "banter4", "banter5", "banter6"];

_play_sound = _sounds call BIS_fnc_SelectRandom;

if (side _unit == civilian) && ((_unit distance player) < 5) then

{_x say3D _play_sound } foreach _unit;

 };

I added the Hintc just to ensure its firing -which it is, wildly in fact so Ill have to take Ruebes point of delay etc.. Curious why its _x say 3D rather than _unit?

 

 Dont know why they're not speaking - is there some weird conflict between the Civilian who gets intially detected via the trigger and _unit?? The sounds themselves are all working as intended as if I call a simple playsound "banter1" - they all work.

 

 So again my trigger which is named Double is first attached to player via 2m radius with a Civilian Present This condition and set to repeatedly. The OnAct: x= call fnc_civ.

 

@ruebe:

Why not spawn a simple FSM

 

 

 Have you ever measured the temperature of a brass toilet on the shady side of an iceberg? Wells thats pretty much my IQ on such matters :P

 

Srsly tho once I get this thing working Ill take all your advice into consideration

 

. One more question: How do I isolate the Civilian triggering the trigger? Meaning what variable would I put in the OnAct to make that one Civilian use Say3D?  'this'?

Share this post


Link to post
Share on other sites

As rübe said, use a FSM or a script for performance reasons.

I'd use nearEntities to check for civilians, it only detects alive units and is pretty fast.

You could also use setVariable on the player to save recently used sounds and exclude them from being said again within a certain time period to provide authenticity.

 

Cheers

Share this post


Link to post
Share on other sites
fnc_Civ = {

_person = (position player) nearEntities ["Man",5];

Hint "Im working!!";

_sounds = ["banter1", "banter2", "banter3", "banter4", "banter5", "banter6"];

_play_sound = _sounds call BIS_fnc_SelectRandom;


_person say3D _play_sound;

sleep5;

 };

 Works now :)

 

 For some reason the if ( side_person ==civilian) then blah blah was killing it tho i have no idea why. The trigger is already called by Civilian so maybe redundent? Dunno, this stuff makes my head spin. Thanks guys, ill use the expensive trigger for now and then try and clean it up after mission is completed along with much else ;)

Share this post


Link to post
Share on other sites

 For some reason, the say3d in this script plays but definitely doesnt sound like its coming from that civilian but played generically -more like a playsound.

 

 Ive tried now to attach an object to the head of the civilian:

private ["_pos", "_mouth", "_person", "_play_sound"];

fnc_Civ = {

_person = (position player) nearEntities ["Man",2];
_pos = position vehicle _person;


Hint "Im working!!";

_sounds = ["banter1", "banter2", "banter3", "banter4", "banter5", "banter6", "scunty"];

_play_sound = _sounds call BIS_fnc_SelectRandom;

_person doWatch player;




_mouth = "Land_HelipadEmpty_F" createVehicleLocal _pos;    
_mouth attachto [_person, [0,0,0],"head"];
_mouth say3d _play_sound;


sleep5;

 };

 ..but get an error with the_pos error vehicle array,  expected object. Not sure why _pos is coming back as an array and not as that one civilian..?

Share this post


Link to post
Share on other sites

nearEntities returns an array, meaning even if you're only near one unit you will get 

_person=[unit1];

_pos=position vehicle [unit1];<---This throws the error.

 

Simplest solution is

_person=((position player) nearEntities ["Man",2]) select 0;

 

Working on the basis if you've got two people close enough together then only one of them saying something is reasonable.

Share this post


Link to post
Share on other sites

nearEntities returns an array, meaning even if you're only near one unit you will get 

_person=[unit1];

_pos=position vehicle [unit1];<---This throws the error.

 

Simplest solution is

_person=((position player) nearEntities ["Man",2]) select 0;

 

Working on the basis if you've got two people close enough together then only one of them saying something is reasonable.

This this SO MUCH _THIS!!!!!!

 

Thanks man :)

 

 Actually this helps me in so many areas of my mission -i had a hard time just getting the damn 'unit' i needed. How would one know it was select 0? Its picking the 1st object in the array closest to Player?

Share this post


Link to post
Share on other sites

Pretty much yeah, I think nearEntities returns an array sorted by distance with nearest first, (array elements are indexed starting from 0). Since you're using a very small radius it's not a major issue if it isn't, but otherwise you could use Bis_fnc_sortBy to find the one that is actually nearest.

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
Sign in to follow this  

×