thy_ 130 Posted February 27, 2022 Context: on Dedicated Server / not tested in hosted server Hello again, This is my first script with function structure and I'm facing a hard time learning the syntaxes and the logic needed to make this work properly when with more than one player in-game. My mistakes are potentially in fn_VO_globalFunctions.sqf file and how I am calling that in fn_VO_coreGround.sqf file. Btw, this mission is not using any init file. Bad behaviors: Only repairing is working for everyone. Refueling and rearming are not working at all. Nobody can't see the systemChat feedback messages. description.ext class cfgFunctions { // VEHICLE OVERHAULING: REPAIR, REARM, REFUEL #include "vehiclesOverhauling\THY_functions.hpp" }; THY_functions.hpp class THY_functions { tag = "THY"; class vehiclesOverhauling { file = "vehiclesOverhauling"; class VO_parameters { preInit = 1 }; class VO_globalFunctions { preInit = 1 }; class VO_coreGround { preInit = 1 }; //class VO_coreAir { preInit = 1 }; //class VO_coreNautic { preInit = 1 }; }; }; fn_VO_parameters.sqf // EDITOR'S OPTIONS: VO_debugMonitor = false; // true = turn on the editor hints / false = turn it off. VO_feedbackMsgs = true; // true = the station shows service messages in-game for the player (highly recommended) / false = turn it off. // GROUND SERVICES groundVehiclesOverhauling = true; // true = the station accepts ground vehicles / false = doesn't accept. VO_groundServRepair = true; // true = repairing for ground veh is available / false = not available / highly recommended turn it on if you want also to refueling. VO_groundServRefuel = true; // true = refueling for ground veh is available / false = not available. VO_groundServRearm = true; // true = rearming for ground veh is available / false = not available. VO_grdActRange = 10; // in meters, the area around the station that identifies the ground vehicle to be serviced. Default 10. VO_grdCooldown = 10; // in seconds, time among each available ground services. Default 10. VO_grdStationAssets = // which assets (classnames) will be automatically ground stations on mission. [ "Land_RepairDepot_01_green_F", "Land_RepairDepot_01_tan_F" ]; // AIR SERVICES airVehiclesOverhauling = true; // true = the station accepts air vehicles / false = doesn't accept. VO_airServRepair = true; // true = repairing for air veh is available / false = not available / highly recommended turn it on if you want also to refueling. VO_airServRefuel = true; // true = refueling for air veh is available / false = not available. VO_airServRearm = true; // true = rearming for air veh is available / false = not available. VO_airActRange = 20; // in meters, the area around the station that identifies the air vehicle to be serviced. Default 10. VO_airCooldown = 10; // in seconds, time among each available air services. Default 10. VO_airStationAssets = // which assets (classnames) will be automatically air stations on mission. [ "Land_HelipadRescue_F", "Land_HelipadSquare_F", "Land_HelipadCircle_F", "Land_HelipadCivil_F" ]; // NAUTIC SERVICES nauticVehiclesOverhauling = true; // true = the station accepts nautic vehicles / false = doesn't accept. VO_nauticServRepair = true; // true = repairing for nautic veh is available / false = not available / highly recommended turn it on if you want also to refueling. VO_nauticServRefuel = true; // true = refueling for nautic veh is available / false = not available. VO_nauticServRearm = true; // true = rearming for nautic veh is available / false = not available. VO_nauActRange = 25; // in meters, the area around the station that identifies the nautic vehicle to be serviced. Default 10. VO_nauCooldown = 10; // in seconds, time among each available nautic services. Default 10. VO_nauStationAssets = // which assets (classnames) will be automatically nautic stations on mission. [ "Land_TBox_F" ]; true fn_VO_globalFunctions.sqf THY_fnc_VO_humanPlayersAlive = { private ["_headlessClients"]; _headlessClients = entities "HeadlessClient_F"; VO_humanPlayersAlive = (allPlayers - _headlessClients) select {alive _x}; true }; THY_fnc_VO_debugMonitor = { //WIP true }; fn_VO_coreGround.sqf //if (!isServer) exitWith {}; private ["_arrayGroundStations","_groundVehicles","_serviceInProgress","_eachGroundStation",/*"_grdRepairNeeded","_grdRefuelNeeded","_grdRearmNeeded",*/"_eachHumamPlayer"]; [] spawn { // arrays that will be populated only with the objects classnames listed by VO_grdStationAssets. _arrayGroundStations = []; // initial services condition _serviceInProgress = false; // if ground services is allowed... finding out only the objects of classnames listed in VO_grdStationAssets through the allMissionsObjects. if ( groundVehiclesOverhauling == true ) then { { _arrayGroundStations = _arrayGroundStations + allMissionObjects _x } forEach VO_grdStationAssets }; // check whether or not run this while-looping / if some or all services are on, bota pra foder... while { groundVehiclesOverhauling == true } do { // check who's human here: call THY_fnc_VO_humanPlayersAlive; { // VO_humanPlayersAlive forEach starts... _eachHumamPlayer = _x; if ( VO_debugMonitor == true ) then { call THY_fnc_VO_debugMonitor }; // defining the ground veh of _eachHumamPlayer (_x) into XXm radius: _groundVehicles = _x nearEntities [["Car", "Motorcycle", "Tank", "WheeledAPC", "TrackedAPC"], 10]; { // forEach of _arrayGroundStations starts... _eachGroundStation = _x; { // forEach of _groundVehicles starts... if ( (_x distance _eachGroundStation) < VO_grdActRange ) then { sleep 3; // a breath before the any ground service. // GROUND REPAIR if (VO_groundServRepair == true) then { if ( (alive _x) AND (damage _x > 0.1) AND (isEngineOn _x == false) AND (speed _x < 2) AND (_serviceInProgress == false) ) then { _serviceInProgress = true; sleep 3; if (VO_feedbackMsgs == true) then { systemChat "Checking the damages..."; }; playSound3D ["a3\sounds_f\characters\cutscenes\dirt_acts_carfixingwheel.wss", _eachGroundStation]; sleep 3; playSound3D ["a3\sounds_f\sfx\ui\vehicles\vehicle_repair.wss", _x]; // if player inside the vehicle: if (!isNull objectParent _eachHumamPlayer) then { addCamShake [1, 5, 5]; // [power, duration, frequency]. }; _x setDammage 0; sleep 3; if (VO_feedbackMsgs == true) then { systemChat "Ground vehicle has been repaired!"; sleep 2; if ( ( (VO_groundServRefuel == true) OR (VO_groundServRearm == true) ) AND ( (fuel _x < 0.8) OR ( ({getNumber (configFile >> "CfgMagazines" >> _x select 0 >> "count") != _x select 1} count (magazinesAmmo _x)) > 0 ) ) ) then { systemChat "Preparing to the next service..."; }; }; sleep VO_grdCooldown; _serviceInProgress = false; // station is free for the next service! }; }; // GROUND REFUEL if (VO_groundServRefuel == true) then { if ( (alive _x) AND (fuel _x < 0.8) AND (isEngineOn _x == false) AND (speed _x < 2) AND (_serviceInProgress == false) ) then { _serviceInProgress = true; sleep 3; if (VO_feedbackMsgs == true) then { systemChat "Checking the fuel..."; }; playSound3D ["a3\sounds_f\characters\cutscenes\concrete_acts_walkingchecking.wss", _eachGroundStation]; sleep 3; playSound3D ["a3\sounds_f\sfx\ui\vehicles\vehicle_refuel.wss", _x]; if (!isNull objectParent _eachHumamPlayer) then { addCamShake [0.3, 5, 2]; }; _x setFuel 1; sleep 3; if (VO_feedbackMsgs == true) then { systemChat "Ground vehicle has been refueled!"; sleep 2; if ( ( (VO_groundServRepair == true) OR (VO_groundServRearm == true) ) AND ( (damage _x > 0.1) OR ( ({getNumber (configFile >> "CfgMagazines" >> _x select 0 >> "count") != _x select 1} count (magazinesAmmo _x)) > 0 ) ) ) then { systemChat "Preparing to the next service..."; }; }; sleep VO_grdCooldown; _serviceInProgress = false; }; }; // GROUND REARM if (VO_groundServRearm == true) then { if ( (alive _x) AND ( ({getNumber (configFile >> "CfgMagazines" >> _x select 0 >> "count") != _x select 1} count (magazinesAmmo _x)) > 0 ) AND (speed _x < 2) AND (_serviceInProgress == false) ) then { _serviceInProgress = true; sleep 3; if (VO_feedbackMsgs == true) then { systemChat "Checking the ammunition..."; }; playSound3D ["a3\sounds_f\characters\cutscenes\concrete_acts_walkingchecking.wss", _eachGroundStation]; sleep 3; playSound3D ["a3\sounds_f\sfx\ui\vehicles\vehicle_rearm.wss", _x]; if (!isNull objectParent _eachHumamPlayer) then { addCamShake [1, 5, 3]; }; _x setVehicleAmmo 1; sleep 3; if (VO_feedbackMsgs == true) then { systemChat "Ground vehicle has been rearmed!"; sleep 2; if ( ( (VO_groundServRepair == true) OR (VO_groundServRefuel == true) ) AND ( (damage _x > 0.1) OR (fuel _x < 0.8) ) ) then { if (isEngineOn _x == false) then { systemChat "Preparing to the next service..."; } else { systemChat "For the next service, turn off the engine!"; }; }; }; sleep VO_grdCooldown; _serviceInProgress = false; }; }; }; } forEach _groundVehicles; } forEach _arrayGroundStations; } forEach VO_humanPlayersAlive; sleep 5; }; }; // spawn ends. Editable mission download: https://github.com/aldolammel/arma-3-vehicles-overhauling Share this post Link to post Share on other sites
7erra 629 Posted February 27, 2022 The github link is 404 (not found). As for your problems: that sounds like a locality issue. setDamage takes a global argument while setFuel and setVehicleAmmo require the vehicle to be local. Same issue with systemChat, the command has a local effect so you have to remoteExec that on the player that should see the message. 1 Share this post Link to post Share on other sites
thy_ 130 Posted February 27, 2022 17 hours ago, 7erra said: The github link is 404 (not found). Now the Github repository is public! EDITED FEB 27th: 17 hours ago, 7erra said: setDamage takes a global argument while setFuel and setVehicleAmmo require the vehicle to be local. Oh, now I got it why these icon below. Cool, @7erra. I will study remoteExec today and make my tries. Share this post Link to post Share on other sites
thy_ 130 Posted February 27, 2022 So, I'll test these changes on the dedicated server tonight: * Edited with the last @7erra advice in Feb, 28th: // FROM THIS: systemChat "Checking the ammunition..."; // TO THIS: ["Checking the ammunition..."] remoteExec ["systemChat", _x]; // ------------- // FROM THIS: _x setFuel 1; // TO THIS: [_x, 1] remoteExec ["setFuel", _x]; // ------------- // FROM THIS: _x setVehicleAmmo 1; // TO THIS: [_x, 1] remoteExec ["setVehicleAmmo", _x]; Later I go back with the result. * Edited: worked very well in server hosted and dedicated server 😉 Share this post Link to post Share on other sites
thy_ 130 Posted February 27, 2022 5 hours ago, thy_ said: Later I go back with the result. Working with multiple players on a dedicated server beautifully, @7erra! 😉 Share this post Link to post Share on other sites
7erra 629 Posted February 28, 2022 instead of asking everyone to execute setVehicleAmmo and setFuel you can target the vehicle's owner directly: [_x, 1] remoteExec ["setVehicleAmmo", _x]; This should reduce network traffic 1 Share this post Link to post Share on other sites
thy_ 130 Posted February 28, 2022 1 minute ago, 7erra said: instead of asking everyone to execute setVehicleAmmo and setFuel you can target the vehicle's owner directly: [_x, 1] remoteExec ["setVehicleAmmo", _x]; This should reduce network traffic How? Share this post Link to post Share on other sites
7erra 629 Posted February 28, 2022 Just like I wrote. You can specifiy a target as the second param in the right hand argument, in this case _x (the vehicle, or rather the machine to which the vehicle is local) 1 Share this post Link to post Share on other sites