diff --git a/README.md b/README.md index 226a3cd..8db018b 100644 --- a/README.md +++ b/README.md @@ -78,4 +78,49 @@ All modules are broken apart as such in /framework. Client and server inits are Pay attention to framework/script_mod.hpp prior to deployment of releases, as the debug settings within will determine what is logged during prod missions. -CfgFunctions is sensitive to the folder/script_component.hpp of each module. \ No newline at end of file +CfgFunctions is sensitive to the folder/script_component.hpp of each module. + +### `defines` Directory + +This directory contains a number of hpp files used to define constants throughout the framework. These should ONLY be edited by or with the supervision of a developer to reflect format battalion-wide changes. + +- `ApprovedAssets.hpp`: Contains subclasses for approved aerial assets with their assigned callsigns. Used primarily in `fbcb2_assets`. +- `BattalionInfo.hpp`: Used for representing Battalion structure, element callsigns, and radio frequency assignments. Used primarily in `fbcb2_main`. +- `DisallowedEquipment.hpp`: Contains flagged item classnames by category that players may not use, or may use only in specific roles. Used to monitor and enforce equipment restrictions. +- `SignalColors.hpp`: Contains smoke/flare/chemlight colors and what they represent in the field. Used primarily in `fbcb2_main` for the Signal Colors diary record. +- `SupplyCrates.hpp`: Contains the types, contents, and metadata for all supply crate types in the `resupply` module. +- `VehicleFlags.hpp`: Defines system information, flag categories, and flag options used to populate ACE3 interaction menus for vehicles. Used by the `vehicleFlags` module. + + +### Modules List + +*Within `framework`:* + +- `ambience`: + - Adds ambient flak capabilities. +- `client`: + - Contains core client-side event handlers and actions that don't fit into other modules. +- `common`: + - Contains common functions and variables used by multiple modules. +- `fbcb2_main`: + - Contains the main FBCB2 functionality and initialization code. Populates the briefing/diary with mission information. +- `fbcb2_assets`: + - A subcomponent of `fbcb2_main`. Used to gather, display, and manage diary records as intel for assets near known bases. +- `init`: + - Contains core initialization functions. Both server and client inits across all modules are managed here. +- `mapcopy`: + - Gives players the ability to copy each other's maps. +- `performance`: + - Contains functionality for monitoring and logging performance data. +- `reinsert`: + - Provides a reinsertion queue system for players and pilots to maximize efficiency of the reinsertion process. +- `resupply`: + - Provides a Zeus module and standalone function to spawn pre-equipped supply crates onto the battlefield. + - Supply crate definitions are stored in `defines/SupplyCrates.hpp`. + - Optionally, allows players to spawn supply crates from arsenal boxes. +- `triageIcons`: + - For those with medical permissions (`ace_medical`), provides a configurable 3D icon over unconscious units indicating their current ACE Triage Card status. +- `vehicleFlags`: + - Provides an ACE3 interaction menu that allows players to attach and remove flags from vehicles. + - Flags are defined in `defines/VehicleFlags.hpp`. + diff --git a/defines/VehicleFlags.hpp b/defines/VehicleFlags.hpp index fce9606..2e13fb2 100644 --- a/defines/VehicleFlags.hpp +++ b/defines/VehicleFlags.hpp @@ -125,5 +125,40 @@ class VehicleFlags { texture = "textures\flags_misc\flag_redcross_co.paa"; }; }; + + class BuiltIn { + actionID = "flag_builtin"; + actionTitle = "Built-In"; + class BlueFlag { + actionID = "flag_builtin_blue"; + actionTitle = "Blue Flag"; + texture = "\A3\Data_F\Flags\flag_blue_CO.paa"; + }; + class GreenFlag { + actionID = "flag_builtin_green"; + actionTitle = "Green Flag"; + texture = "\A3\Data_F\Flags\flag_green_CO.paa"; + }; + class RedFlag { + actionID = "flag_builtin_red"; + actionTitle = "Red Flag"; + texture = "\A3\Data_F\Flags\flag_red_CO.paa"; + }; + class WhiteFlag { + actionID = "flag_builtin_white"; + actionTitle = "White Flag"; + texture = "\A3\Data_F\Flags\flag_white_CO.paa"; + }; + class NATOFlag { + actionID = "flag_builtin_nato"; + actionTitle = "NATO Flag"; + texture = "\A3\Data_F\Flags\flag_NATO_CO.paa"; + }; + class UNFlag { + actionID = "flag_builtin_un"; + actionTitle = "UN Flag"; + texture = "\A3\Data_F\Flags\Flag_uno_CO.paa"; + }; + }; }; }; \ No newline at end of file diff --git a/framework/CfgFunctions.hpp b/framework/CfgFunctions.hpp index d9e5f96..bfe7d28 100644 --- a/framework/CfgFunctions.hpp +++ b/framework/CfgFunctions.hpp @@ -12,7 +12,6 @@ class CfgFunctions { class addRespawnChatHandler { postInit = 1; }; }; }; - class PREFIX { class ambience { @@ -20,35 +19,25 @@ class CfgFunctions { class flakInitVehicle {}; class flakEH {}; }; - - class map { - file = "framework\map"; - class initMapCopy { postInit = 1; }; - class copyMapFromPlayer {}; //needs refactor - class getPlayerMapMarkers {}; //needs refactor - class loadMapMarkers {}; //needs refactor - class mapMarkerToString {}; //needs refactor - class stringToMapMarker {}; //needs refactor - }; }; class DOUBLES(PREFIX,client) { class functions { file = "framework\client\functions"; - class addZenModules { postInit = 1; }; class bindEmptyGroupGarbageCleanup { postInit = 1; }; class bindEventHandlers { postInit = 1; }; class bindVehicleActions { postInit = 1; }; + class addZenModules {postInit = 1;}; }; }; - class DOUBLES(PREFIX,common) { class functions { file = "framework\common\functions"; class addCBASettings { preInit = 1; }; class logMissionInfo {}; class addPlayerInfoToArray {}; + class createOrUpdateDiaryRecord {}; class getApprovedAssetsCfg {}; class getBattalionCfg {}; class getNameOfBase {}; @@ -95,12 +84,23 @@ class CfgFunctions { }; class util { file = "framework\fbcb2_main\util"; - class createOrUpdateDiaryRecord {}; class formatRadioElementForDiary {}; class generateElementFrequencyRecordText {}; }; }; + class DOUBLES(PREFIX,mapcopy) { + class functions { + file = "framework\mapcopy\functions"; + class addCBASettings {preInit=1;}; + class initClient {}; + class getMapMarkers {}; + class loadMapMarkers {}; + class mapMarkerToString {}; + class stringToMapMarker {}; + }; + }; + class DOUBLES(PREFIX,performance) { class functions { file = "framework\performance\functions"; @@ -169,4 +169,12 @@ class CfgFunctions { class isClassExcluded {}; }; }; + + class DOUBLES(PREFIX,zeus) { + class functions { + file = "framework\zeus\functions"; + class initClient {}; + class addZenModules {}; + }; + }; }; \ No newline at end of file diff --git a/framework/client/functions/fn_addZenModules.sqf b/framework/client/functions/fn_addZenModules.sqf index 0aeb533..d59ff07 100644 --- a/framework/client/functions/fn_addZenModules.sqf +++ b/framework/client/functions/fn_addZenModules.sqf @@ -2,61 +2,6 @@ if ( !hasInterface ) exitWith {}; -[ - QUOTE(MODULE_CATEGORY_NAME), - "Create Resupply Box", - { - params [["_pos", [0,0,0], [[]], 3], ["_target", objNull, [objNull]]]; - // get parent definition - private _supplyCratesCfg = call EFUNC(resupply,getSupplyCratesCfg); - // get the subclass names - private _boxTypesAvailable = _supplyCratesCfg call BIS_fnc_getCfgSubClasses; - - _boxTypesAvailable sort true; - _comboOptions = _boxTypesAvailable apply { - [ - // display name - [_supplyCratesCfg >> _x >> "displayName", "STRING", "ERROR"] call CBA_fnc_getConfigEntry, - // tooltip - [_supplyCratesCfg >> _x >> "tooltip", "STRING", "ERROR"] call CBA_fnc_getConfigEntry, - // icon - [_supplyCratesCfg >> _x >> "icon", "STRING", "ERROR"] call CBA_fnc_getConfigEntry - ] - }; - - [ - "Resupply Box Options", - [ - // [ "COMBO", "Box Type", [[1,2,3], [["Ammo"],["Weapons"],["Medical"]],0] ] - ["COMBO", "Box Type", [_boxTypesAvailable, _comboOptions, 0]] - ], - { - - params ["_dialog", "_args"]; - - _dialog params ["_typeOptionSelected"]; - _args params ["_pos", "_target", "_keysSorted"]; - - - private _box = [_target, _typeOptionSelected, _pos] call EFUNC(resupply,createBox); - if (isNull _box) exitWith { - ["Resupply Box", "WARNING: Failed to locate or create box!"] call BIS_fnc_curatorHint; - }; - [ - "Resupply Box", - format[ - "Created %1", - getText((call EFUNC(resupply,getSupplyCratesCfg)) >> _typeOptionSelected >> "displayName") - ] - ] call BIS_fnc_curatorHint; - }, - {}, - [_pos, _target] - ] call zen_dialog_fnc_create; - } -] call zen_custom_modules_fnc_register; - - [ QUOTE(MODULE_CATEGORY_NAME), "Grounds Cleanup", diff --git a/framework/fbcb2_main/util/fn_createOrUpdateDiaryRecord.sqf b/framework/common/functions/fn_createOrUpdateDiaryRecord.sqf similarity index 80% rename from framework/fbcb2_main/util/fn_createOrUpdateDiaryRecord.sqf rename to framework/common/functions/fn_createOrUpdateDiaryRecord.sqf index 7f04abb..2b790d9 100644 --- a/framework/fbcb2_main/util/fn_createOrUpdateDiaryRecord.sqf +++ b/framework/common/functions/fn_createOrUpdateDiaryRecord.sqf @@ -3,12 +3,21 @@ if (!hasInterface) exitWith {}; params [ - ["_subjectID", GVAR(subjectStatusID), [""]], + ["_subjectID", "", [""]], ["_recordTitle", "", [""]], ["_recordText", "", [""]], ["_recordIcon", "", [""]] ]; +// Check if all parameters are provided +if ( + count _subjectID isEqualTo 0 || + count _recordTitle isEqualTo 0 || + count _recordText isEqualTo 0 +) exitWith { + [LEVEL_ERROR, QUOTE(COMPONENT), "Not all parameters provided"] call EFUNC(common,log); +}; + // Check if already created private _subjectRecords = GVAR(diaryRecords) getOrDefault [_subjectID, createHashMap, true]; private _existingRecord = _subjectRecords getOrDefault [_recordTitle, diaryRecordNull, true]; diff --git a/framework/fbcb2_assets/functions/fn_initClient.sqf b/framework/fbcb2_assets/functions/fn_initClient.sqf index 62dfbf3..c18b012 100644 --- a/framework/fbcb2_assets/functions/fn_initClient.sqf +++ b/framework/fbcb2_assets/functions/fn_initClient.sqf @@ -21,7 +21,7 @@ call FUNC(updateAssetDiary); [ LEVEL_DEBUG, QUOTE(COMPONENT), - "postInit complete", + "initClient complete", [] ] call EFUNC(common,log); diff --git a/framework/fbcb2_assets/functions/fn_updateAssetDiary.sqf b/framework/fbcb2_assets/functions/fn_updateAssetDiary.sqf index 72e516d..d2669d5 100644 --- a/framework/fbcb2_assets/functions/fn_updateAssetDiary.sqf +++ b/framework/fbcb2_assets/functions/fn_updateAssetDiary.sqf @@ -241,7 +241,7 @@ private _randomColors = [ ], _recordText joinString "
", _icon - ] call EFUNC(fbcb2_main,createOrUpdateDiaryRecord); + ] call EFUNC(common,createOrUpdateDiaryRecord); // "\A3\ui_f\data\igui\cfg\simpleTasks\types\car_ca.paa" } forEach _distinctVehiclesClassNames; diff --git a/framework/fbcb2_main/functions/fn_addEnvironmentRecord.sqf b/framework/fbcb2_main/functions/fn_addEnvironmentRecord.sqf index 3cc7dda..8aff10b 100644 --- a/framework/fbcb2_main/functions/fn_addEnvironmentRecord.sqf +++ b/framework/fbcb2_main/functions/fn_addEnvironmentRecord.sqf @@ -109,4 +109,4 @@ _text = _text joinString "
"; GVAR(subjectIntelID), _recordTitle, _text -] call FUNC(createOrUpdateDiaryRecord); \ No newline at end of file +] call EFUNC(common,createOrUpdateDiaryRecord); \ No newline at end of file diff --git a/framework/fbcb2_main/functions/fn_addFrequenciesRecord.sqf b/framework/fbcb2_main/functions/fn_addFrequenciesRecord.sqf index 9f5cccb..ae10cf0 100644 --- a/framework/fbcb2_main/functions/fn_addFrequenciesRecord.sqf +++ b/framework/fbcb2_main/functions/fn_addFrequenciesRecord.sqf @@ -62,7 +62,7 @@ reverse _battalionElementCfgs; GVAR(subjectFrequenciesID), _diaryTitleText#0, _diaryTitleText#1 - ] call FUNC(createOrUpdateDiaryRecord); + ] call EFUNC(common,createOrUpdateDiaryRecord); } forEach _battalionElementCfgs; // add the battalion command to the top of the list @@ -72,6 +72,6 @@ private _diaryTitleText = [_battalionInfoCfg >> "Command", false] call FUNC(gene GVAR(subjectFrequenciesID), _diaryTitleText#0, _diaryTitleText#1 -] call FUNC(createOrUpdateDiaryRecord); +] call EFUNC(common,createOrUpdateDiaryRecord); true; \ No newline at end of file diff --git a/framework/fbcb2_main/functions/fn_addSignalColorsRecord.sqf b/framework/fbcb2_main/functions/fn_addSignalColorsRecord.sqf index 078c72f..ae712de 100644 --- a/framework/fbcb2_main/functions/fn_addSignalColorsRecord.sqf +++ b/framework/fbcb2_main/functions/fn_addSignalColorsRecord.sqf @@ -56,4 +56,4 @@ _text = _text joinString "

"; GVAR(subjectIntelID), _recordTitle, _text -] call FUNC(createOrUpdateDiaryRecord); \ No newline at end of file +] call EFUNC(common,createOrUpdateDiaryRecord); \ No newline at end of file diff --git a/framework/fbcb2_main/functions/fn_initClient.sqf b/framework/fbcb2_main/functions/fn_initClient.sqf index b2f717b..e0cc5cb 100644 --- a/framework/fbcb2_main/functions/fn_initClient.sqf +++ b/framework/fbcb2_main/functions/fn_initClient.sqf @@ -25,12 +25,6 @@ player createDiarySubject[GVAR(subjectAssetsFixedWingID), "FBCB2 Planes"]; player createDiarySubject[GVAR(subjectAssetsRotaryID), "FBCB2 Helicopters"]; player createDiarySubject[GVAR(subjectAssetsGroundID), "FBCB2 Ground"]; -// store records in format: -// [subject, [ -// [title, diaryRecord] -// ]] -GVAR(diaryRecords) = createHashMap; - // run main inits [] call FUNC(addFrequenciesRecord); [] call FUNC(addSignalColorsRecord); @@ -47,7 +41,7 @@ GVAR(diaryRecords) = createHashMap; [ LEVEL_DEBUG, QUOTE(COMPONENT), - "postInit complete", + "initClient complete", [] ] call EFUNC(common,log); diff --git a/framework/init/functions/fn_addRespawnChatHandler.sqf b/framework/init/functions/fn_addRespawnChatHandler.sqf index b2d0007..6e4c22f 100644 --- a/framework/init/functions/fn_addRespawnChatHandler.sqf +++ b/framework/init/functions/fn_addRespawnChatHandler.sqf @@ -24,7 +24,7 @@ [ LEVEL_INFO, QUOTE(COMPONENT), - "Respawn chat handler registered", + "respawn chat handler registered", [player] call EFUNC(common,addPlayerInfoToArray) ] call EFUNC(common,log); diff --git a/framework/init/functions/fn_initClient.sqf b/framework/init/functions/fn_initClient.sqf index a7d106a..6e82106 100644 --- a/framework/init/functions/fn_initClient.sqf +++ b/framework/init/functions/fn_initClient.sqf @@ -14,12 +14,21 @@ waitUntil {!isNil QGVARMAIN(complete)}; ["InitializePlayer", [player, true]] call BIS_fnc_dynamicGroups; +// Initialize a holder for managing local diary records +// store records in format: +// [subject, [ +// [title, diaryRecord] +// ]] +EGVAR(common,diaryRecords) = createHashMap; + // initialize other modules +call EFUNC(mapcopy,initClient); call EFUNC(reinsert,initClient); call EFUNC(resupply,initClient); call EFUNC(triageIcons,initClient); call EFUNC(vehicleFlags,initClient); +call EFUNC(zeus,initClient); call EFUNC(fbcb2_main,initClient); call EFUNC(fbcb2_assets,initClient); @@ -27,8 +36,10 @@ call EFUNC(fbcb2_assets,initClient); [ LEVEL_DEBUG, QUOTE(COMPONENT), - "postInit complete", + "initClient complete", [] ] call EFUNC(common,log); +localNamespace setVariable [QGVAR(complete), true]; + nil; \ No newline at end of file diff --git a/framework/map/fn_copyMapFromPlayer.sqf b/framework/map/fn_copyMapFromPlayer.sqf deleted file mode 100644 index 16d988e..0000000 --- a/framework/map/fn_copyMapFromPlayer.sqf +++ /dev/null @@ -1,5 +0,0 @@ -params ["_sourcePlayer","_destinationPlayer"]; - -hint format["Copying map markers from %1", name _sourcePlayer]; - -[_destinationPlayer] remoteExecCall ["milsim_fnc_getPlayerMapMarkers",_sourcePlayer]; diff --git a/framework/map/fn_getPlayerMapMarkers.sqf b/framework/map/fn_getPlayerMapMarkers.sqf deleted file mode 100644 index 299985c..0000000 --- a/framework/map/fn_getPlayerMapMarkers.sqf +++ /dev/null @@ -1,16 +0,0 @@ -params ["_destinationPlayer"]; - -_markerData = []; - -hint format["Your map is being copied by %1", name _destinationPlayer]; - -{ - _marker = toArray _x; - _marker resize 15; - if ( toString _marker == "_USER_DEFINED #" ) then { - _marker = _x call milsim_fnc_mapMarkerToString; - _markerData pushBack _marker; - }; -} forEach allMapMarkers; - -[_markerData] remoteExecCall ["milsim_fnc_loadMapMarkers",_destinationPlayer]; diff --git a/framework/map/fn_initMapCopy.sqf b/framework/map/fn_initMapCopy.sqf deleted file mode 100644 index 7e60c51..0000000 --- a/framework/map/fn_initMapCopy.sqf +++ /dev/null @@ -1,17 +0,0 @@ -_map_copy_condition = -{ - ('ItemMap' in (assignedItems _player)) && ('ItemMap' in (assignedItems _target)) && ([_player, _target, []] call ace_common_fnc_canInteractWith) -}; - -_map_copy_action = -[ - "MilSimCopyMap", - "Copy Map", - "\a3\ui_f\data\igui\cfg\actions\talk_ca.paa", - { - [_target,_player] call milsim_fnc_copyMapFromPlayer - }, - _map_copy_condition -] call ace_interact_menu_fnc_createAction; - -["Man", 0, ["ACE_MainActions"], _map_copy_action, true] call ace_interact_menu_fnc_addActionToClass; \ No newline at end of file diff --git a/framework/map/fn_loadMapMarkers.sqf b/framework/map/fn_loadMapMarkers.sqf deleted file mode 100644 index d01989b..0000000 --- a/framework/map/fn_loadMapMarkers.sqf +++ /dev/null @@ -1,10 +0,0 @@ -params ["_markerList"]; - -if ('ItemMap' in (assignedItems player)) then { - { - _x call milsim_fnc_stringToMapMarker; - } foreach _markerList; - hint format["Map copied!"]; -} else { - hint format["You need a map to copy onto!"]; -}; diff --git a/framework/mapcopy/functions/fn_addCBASettings.sqf b/framework/mapcopy/functions/fn_addCBASettings.sqf new file mode 100644 index 0000000..6e299a3 --- /dev/null +++ b/framework/mapcopy/functions/fn_addCBASettings.sqf @@ -0,0 +1,24 @@ +#include "..\script_component.hpp" + +[ + QGVAR(setting_enable), + "CHECKBOX", + "Allow Map Copying", + [QUOTE(SETTINGS_GROUP_NAME), QUOTE(COMPONENT_BEAUTIFIED)], + true, // default value + true, // is global + { + params ["_value"]; + [ + QGVAR(setting_enable), + _value + ] call EFUNC(common,logSettingChanged); + } +] call CBA_fnc_addSetting; + +[ + LEVEL_INFO, + QUOTE(COMPONENT), + "CREATED SETTINGS", + [] +] call EFUNC(common,log); \ No newline at end of file diff --git a/framework/mapcopy/functions/fn_getMapMarkers.sqf b/framework/mapcopy/functions/fn_getMapMarkers.sqf new file mode 100644 index 0000000..2764dd4 --- /dev/null +++ b/framework/mapcopy/functions/fn_getMapMarkers.sqf @@ -0,0 +1,15 @@ +#include "..\script_component.hpp" +// serializes markers on local machine and returns them as array + +_markerData = []; + +{ + _marker = toArray _x; + _marker resize 15; + if ( toString _marker == "_USER_DEFINED #" ) then { + _marker = _x call FUNC(mapMarkerToString); + _markerData pushBack _marker; + }; +} forEach allMapMarkers; + +_markerData; \ No newline at end of file diff --git a/framework/mapcopy/functions/fn_initClient.sqf b/framework/mapcopy/functions/fn_initClient.sqf new file mode 100644 index 0000000..3287103 --- /dev/null +++ b/framework/mapcopy/functions/fn_initClient.sqf @@ -0,0 +1,57 @@ +#include "..\script_component.hpp" + +//////////////////////////////////////////////////////////////////// +// Create action to copy map markers on all inheritors of CAManBase +//////////////////////////////////////////////////////////////////// +private _mapCopyAction = +[ + QGVAR(actionID), + "Copy Map", + "\a3\ui_f\data\igui\cfg\actions\talk_ca.paa", + { + params ["_target", "_player", "_params"]; + format["Copying map markers from %1", name _target] call CBA_fnc_notify; + [QGVAR(mapCopyRequest), _this, _target] call CBA_fnc_targetEvent; + }, + { + params ["_target", "_player", "_params"]; + [QGVAR(setting_enable)] call CBA_settings_fnc_get && { + ('ItemMap' in (assignedItems _player)) && + ('ItemMap' in (assignedItems _target)) && + ([_player, _target, []] call ace_common_fnc_canInteractWith) + }; + } +] call ace_interact_menu_fnc_createAction; +["CAManBase", 0, ["ACE_MainActions"], _mapCopyAction, true] call ace_interact_menu_fnc_addActionToClass; + +//////////////////////////////////////////////////////////////////// +// Create CBA event to receive requests +//////////////////////////////////////////////////////////////////// +[QGVAR(mapCopyRequest), { + params ["_me", "_requester", "_params"]; + format["Your map is being copied by %1", name _requester] call CBA_fnc_notify; + private _myMarkers = _this call FUNC(getMapMarkers); + [QGVAR(mapCopyResponse), [_me, _myMarkers], _requester] call CBA_fnc_targetEvent; +}] call CBA_fnc_addEventHandler; + +//////////////////////////////////////////////////////////////////// +// Create CBA event to receive responses +//////////////////////////////////////////////////////////////////// +[QGVAR(mapCopyResponse), { + params [["_responder", objNull, [objNull]], ["_markerList", [], [[]]]]; + if ('ItemMap' in (assignedItems player)) then { + [_markerList] call FUNC(loadMapMarkers); + format["Copied %1 markers from %2", count _markerList, name _responder] call CBA_fnc_notify; + } else { + format["You need a map to copy onto!"] call CBA_fnc_notify; + }; +}] call CBA_fnc_addEventHandler; + +[ + LEVEL_DEBUG, + QUOTE(COMPONENT), + "initClient complete", + [] +] call EFUNC(common,log); + +localNamespace setVariable [QGVAR(complete), true]; \ No newline at end of file diff --git a/framework/mapcopy/functions/fn_loadMapMarkers.sqf b/framework/mapcopy/functions/fn_loadMapMarkers.sqf new file mode 100644 index 0000000..804bc82 --- /dev/null +++ b/framework/mapcopy/functions/fn_loadMapMarkers.sqf @@ -0,0 +1,8 @@ +#include "..\script_component.hpp" +// accepts an array of serialized markers and adds them to local map + +params [["_markerList", [], [[]]]]; + +{ + _x call FUNC(stringToMapMarker); +} foreach _markerList; \ No newline at end of file diff --git a/framework/map/fn_mapMarkerToString.sqf b/framework/mapcopy/functions/fn_mapMarkerToString.sqf similarity index 100% rename from framework/map/fn_mapMarkerToString.sqf rename to framework/mapcopy/functions/fn_mapMarkerToString.sqf diff --git a/framework/map/fn_stringToMapMarker.sqf b/framework/mapcopy/functions/fn_stringToMapMarker.sqf similarity index 100% rename from framework/map/fn_stringToMapMarker.sqf rename to framework/mapcopy/functions/fn_stringToMapMarker.sqf diff --git a/framework/mapcopy/script_component.hpp b/framework/mapcopy/script_component.hpp new file mode 100644 index 0000000..1011914 --- /dev/null +++ b/framework/mapcopy/script_component.hpp @@ -0,0 +1,3 @@ +#define COMPONENT mapcopy +#define COMPONENT_BEAUTIFIED Map Copy +#include "../script_mod.hpp" \ No newline at end of file diff --git a/framework/reinsert/client/fn_addAceSelfActions.sqf b/framework/reinsert/client/fn_addAceSelfActions.sqf index a6f66de..5d19ba5 100644 --- a/framework/reinsert/client/fn_addAceSelfActions.sqf +++ b/framework/reinsert/client/fn_addAceSelfActions.sqf @@ -1,69 +1,65 @@ #include "..\script_component.hpp" -params ["_type"]; // string of the object's classname -if (!(_type isKindOf "CAManBase")) exitWith {}; +params [ + ["_types", [], [[]]], // classnames to assign these action to + ["_useInheritance", false, [false]] +]; -if ( - (localNamespace getVariable [QGVAR(fileForReinsertClassesAdded), []]) - find _type != -1 -) exitWith {}; +{ // forEach _types + private _classToAddActionsTo = _x; -private _fileForReinsertAction = [ - QGVAR(fileReinsertRequestAction), - "File Re-insert Request", - "\A3\ui_f\data\igui\cfg\simpleTasks\types\takeoff_ca.paa", - { // statement - params ["_target", "_player", "_params"]; - // find nearest base or location - private _base = [_player] call EFUNC(common,getNearestBase); - private _baseName = [_base] call EFUNC(common,getNameOfBase); - // send event to server - [QGVAR(fileReinsertRequest), [_player, _base]] call CBA_fnc_serverEvent; - // notify player their request was filed - [["Re-insert Request Filed"], [format["Location: %1", _baseName]]] call CBA_fnc_notify; - }, - { // condition - params ["_target", "_player", "_params"]; - // find nearest base or location - private _base = [_player] call EFUNC(common,getNearestBase); - private _baseDistance = _player distance _base; + private _fileForReinsertAction = [ + QGVAR(fileReinsertRequestAction), + "File Re-insert Request", + "\A3\ui_f\data\igui\cfg\simpleTasks\types\takeoff_ca.paa", + { // statement + params ["_target", "_player", "_params"]; + // find nearest base or location + private _base = [_player] call EFUNC(common,getNearestBase); + private _baseName = [_base] call EFUNC(common,getNameOfBase); + // send event to server + [QGVAR(fileReinsertRequest), [_player, _base]] call CBA_fnc_serverEvent; + // notify player their request was filed + [["Re-insert Request Filed"], [format["Location: %1", _baseName]]] call CBA_fnc_notify; + }, + { // condition + params ["_target", "_player", "_params"]; + // find nearest base or location + private _base = [_player] call EFUNC(common,getNearestBase); + private _baseDistance = _player distance _base; - private _maxRangeToReady = missionNamespace getVariable [QGVAR(setting_maxRangeToReady), 400]; - private _existingQueue = missionNamespace getVariable [QGVAR(reinsertionQueue), []]; + private _maxRangeToReady = [QGVAR(setting_maxRangeToReady)] call CBA_settings_fnc_get; + private _existingQueue = missionNamespace getVariable [QGVAR(reinsertionQueue), []]; - // check if module is enabled, player is near a base, and player is not already in the queue - // (serverTime - GVAR(missionStartServerTime)) > 60*5 && // only allow after 15 minutes - missionNamespace getVariable ["milsim_reinsert_setting_reinsertion_enabled", true] && - (_baseDistance < _maxRangeToReady) && - not (_player in (_existingQueue apply {_x#0})) - } -] call ace_interact_menu_fnc_createAction; -[_type, 1, ["ACE_SelfActions"], _fileForReinsertAction, true] call ace_interact_menu_fnc_addActionToClass; + // check if module is enabled, player is near a base, and player is not already in the queue + // (serverTime - GVAR(missionStartServerTime)) > 60*5 && // only allow after 15 minutes + [QGVAR(setting_enabled)] call CBA_settings_fnc_get && + (_baseDistance < _maxRangeToReady) && + not (_player in (_existingQueue apply {_x#0})) + } + ] call ace_interact_menu_fnc_createAction; + [_classToAddActionsTo, 1, ["ACE_SelfActions"], _fileForReinsertAction, _useInheritance] call ace_interact_menu_fnc_addActionToClass; -private _removeFileForReinsertAction = [ - QGVAR(removeReinsertRequestAction), - "Remove Re-insert Request", - "\A3\ui_f\data\igui\cfg\simpleTasks\types\land_ca.paa", - { // statement - params ["_target", "_player", "_params"]; - // send event to server - [QGVAR(removeReinsertRequest), [_player]] call CBA_fnc_serverEvent; - // notify player their request was rescinded - "Re-insert Request Rescinded" call CBA_fnc_notify; - }, - { // condition - params ["_target", "_player", "_params"]; - private _existingQueue = missionNamespace getVariable [QGVAR(reinsertionQueue), []]; - - // check if module is enabled, player is in the queue - // (serverTime - GVAR(missionStartServerTime)) > 60*5 && // only allow after 15 minutes - missionNamespace getVariable ["milsim_reinsert_setting_reinsertion_enabled", true] && - (_player in (_existingQueue apply {_x#0})) - } -] call ace_interact_menu_fnc_createAction; -[_type, 1, ["ACE_SelfActions"], _removeFileForReinsertAction, true] call ace_interact_menu_fnc_addActionToClass; - -private _classesActionsAddedTo = (localNamespace getVariable [QGVAR(fileForReinsertClassesAdded), []]); -_classesActionsAddedTo pushBackUnique _type; -localNamespace setVariable [QGVAR(fileForReinsertClassesAdded), _classesActionsAddedTo]; + private _removeFileForReinsertAction = [ + QGVAR(removeReinsertRequestAction), + "Remove Re-insert Request", + "\A3\ui_f\data\igui\cfg\simpleTasks\types\land_ca.paa", + { // statement + params ["_target", "_player", "_params"]; + // send event to server + [QGVAR(removeReinsertRequest), [_player]] call CBA_fnc_serverEvent; + // notify player their request was rescinded + "Re-insert Request Rescinded" call CBA_fnc_notify; + }, + { // condition + params ["_target", "_player", "_params"]; + private _existingQueue = missionNamespace getVariable [QGVAR(reinsertionQueue), []]; + // check if module is enabled, player is in the queue + // (serverTime - GVAR(missionStartServerTime)) > 60*5 && // only allow after 15 minutes + [QGVAR(setting_enabled)] call CBA_settings_fnc_get && + (_player in (_existingQueue apply {_x#0})) + } + ] call ace_interact_menu_fnc_createAction; + [_classToAddActionsTo, 1, ["ACE_SelfActions"], _removeFileForReinsertAction, _useInheritance] call ace_interact_menu_fnc_addActionToClass; +} forEach _types; \ No newline at end of file diff --git a/framework/reinsert/client/fn_addCheckQueueSelfAction.sqf b/framework/reinsert/client/fn_addCheckQueueSelfAction.sqf index 341e09f..819a01a 100644 --- a/framework/reinsert/client/fn_addCheckQueueSelfAction.sqf +++ b/framework/reinsert/client/fn_addCheckQueueSelfAction.sqf @@ -1,30 +1,28 @@ #include "..\script_component.hpp" -params ["_type"]; // string of the object's classname -if (!(_type isKindOf "CAManBase")) exitWith {}; +params [ + ["_types", [], [[]]], // classnames to assign these action to + ["_useInheritance", false, [false]] +]; -if ( - (localNamespace getVariable [QGVAR(checkReinsertQueueClassesAdded), []]) - find _type != -1 -) exitWith {}; +{ // forEach _types + private _classToAddActionsTo = _x; -private _checkReinsertQueueAction = [ - QGVAR(checkReinsertQueue), - "[PILOT] Check Re-insert Queue", - "\A3\ui_f\data\igui\cfg\simpleTasks\types\land_ca.paa", - { - params ["_target", "_player", "_params"]; - // request notification from the server - call FUNC(requestShowQueue); - // reset last check time - localNamespace setVariable [QGVAR(lastReinsertQueueCheck), diag_tickTime]; - }, - { - missionNamespace getVariable [QGVAR(setting_enabled), true] - } // always allow -] call ace_interact_menu_fnc_createAction; -[_type, 1, ["ACE_SelfActions"], _checkReinsertQueueAction, true] call ace_interact_menu_fnc_addActionToClass; + private _checkReinsertQueueAction = [ + QGVAR(checkReinsertQueue), + "[PILOT] Check Re-insert Queue", + "\A3\ui_f\data\igui\cfg\simpleTasks\types\land_ca.paa", + { + params ["_target", "_player", "_params"]; + // request notification from the server + call FUNC(requestShowQueue); + // reset last check time + localNamespace setVariable [QGVAR(lastReinsertQueueCheck), diag_tickTime]; + }, + { + GVAR(setting_enabled); + } // condition + ] call ace_interact_menu_fnc_createAction; + [_classToAddActionsTo, 1, ["ACE_SelfActions"], _checkReinsertQueueAction, _useInheritance] call ace_interact_menu_fnc_addActionToClass; -private _classesActionsAddedTo = (localNamespace getVariable [QGVAR(checkReinsertQueueClassesAdded), []]); -_classesActionsAddedTo pushBackUnique _type; -localNamespace setVariable [QGVAR(checkReinsertQueueClassesAdded), _classesActionsAddedTo]; \ No newline at end of file +} forEach _types; \ No newline at end of file diff --git a/framework/reinsert/client/fn_initClient.sqf b/framework/reinsert/client/fn_initClient.sqf index f262ffe..e770796 100644 --- a/framework/reinsert/client/fn_initClient.sqf +++ b/framework/reinsert/client/fn_initClient.sqf @@ -5,26 +5,16 @@ if (!hasInterface) exitWith {}; // ACE SELF-INTERACTIONS FOR FILING AND RESCINDING REINSERT REQUESTS NEAR BASE - ALL PLAYERS localNamespace setVariable [QGVAR(fileForReinsertClassesAdded), []]; // add actions to current class -[typeOf player] call FUNC(addAceSelfActions); -// add actions to future classes -["ace_interact_menu_newControllableObject", { - _this call FUNC(addAceSelfActions); -}] call CBA_fnc_addEventHandler; +[["CAManBase"], true] call FUNC(addAceSelfActions); ///////////////////////////////////////////////////// // PILOTS ONLY // ACE SELF-INTERACTIONS FOR CHECKING REINSERT QUEUE - ONLY FOR PILOTS -if ((typeOf player) in ["B_Helipilot_F", "B_helicrew_F"]) then { - localNamespace setVariable [QGVAR(checkReinsertQueueClassesAdded), []]; - localNamespace setVariable [QGVAR(lastReinsertQueueCheck), diag_tickTime]; +localNamespace setVariable [QGVAR(checkReinsertQueueClassesAdded), []]; +localNamespace setVariable [QGVAR(lastReinsertQueueCheck), diag_tickTime]; - // add actions to current class - [typeOf player] call FUNC(addCheckQueueSelfAction); - // add actions to future classes - ["ace_interact_menu_newControllableObject", { - _this call FUNC(addCheckQueueSelfAction); - }] call CBA_fnc_addEventHandler; -}; +// add actions to pilot classes, and don't apply to child classes +[["B_Helipilot_F", "B_helicrew_F"], false] call FUNC(addCheckQueueSelfAction); ///////////////////////////////////////////////////// @@ -33,13 +23,13 @@ if ((typeOf player) in ["B_Helipilot_F", "B_helicrew_F"]) then { [{ // if module not enabled and pilot forced check not enabled, exit if (not ( - missionNamespace getVariable [QGVAR(setting_enabled), true] && - missionNamespace getVariable [QGVAR(setting_pilotForcedCheckEnabled), true] + [QGVAR(setting_enabled)] call CBA_settings_fnc_get and + [QGVAR(setting_pilotForcedCheckEnabled)] call CBA_settings_fnc_get )) exitWith {}; // if last check was less than X minutes ago, skip private _lastCheck = localNamespace getVariable [QGVAR(lastReinsertQueueCheck), diag_tickTime]; - private _requiredCheckInterval = missionNamespace getVariable [QGVAR(setting_pilotForcedCheckInterval), 60*20]; + private _requiredCheckInterval = [QGVAR(setting_pilotForcedCheckInterval)] call CBA_settings_fnc_get; if ( diag_tickTime - _lastCheck < _requiredCheckInterval @@ -57,6 +47,8 @@ if ((typeOf player) in ["B_Helipilot_F", "B_helicrew_F"]) then { [ LEVEL_DEBUG, QUOTE(COMPONENT), - "postInit complete", + "initClient complete", [] -] call EFUNC(common,log); \ No newline at end of file +] call EFUNC(common,log); + +localNamespace setVariable [QGVAR(complete), true]; \ No newline at end of file diff --git a/framework/resupply/functions/fn_addArsenalObjectSpawnBoxActions.sqf b/framework/resupply/functions/fn_addArsenalObjectSpawnBoxActions.sqf index 74977f9..b1f8f65 100644 --- a/framework/resupply/functions/fn_addArsenalObjectSpawnBoxActions.sqf +++ b/framework/resupply/functions/fn_addArsenalObjectSpawnBoxActions.sqf @@ -35,9 +35,7 @@ private _supplyCrateTypesCfgs = _supplyCratesCfg call BIS_fnc_returnChildren; private _cfg = _x; private _supplyCrateDisplayName = (_cfg >> "displayName") call BIS_fnc_getCfgData; - - - + // add action to spawn supply crate private _actionID = _arsenalBox addAction [format ["Spawn %1", _supplyCrateDisplayName], { params ["_target", "_caller", "_actionId", "_arguments"]; _arguments params ["_supplyCrateCfg"]; @@ -46,13 +44,16 @@ private _supplyCrateTypesCfgs = _supplyCratesCfg call BIS_fnc_returnChildren; configName _supplyCrateCfg, getPos _target ] call FUNC(createBox); + // log action use in server RPT + private _supplyCrateDisplayName = (_supplyCrateCfg >> "displayName") call BIS_fnc_getCfgData; [ LEVEL_INFO, QUOTE(COMPONENT), "Supply crate spawned", [player, [ - ["supplyCrateType", _supplyCrateDisplayName], + ["supplyCrateDisplayName", _supplyCrateDisplayName], + ["supplyCrateCfgName", configName _supplyCrateCfg], ["position", getPos _target] ]] call EFUNC(common,addPlayerInfoToArray) ] remoteExec [QEFUNC(common,log), 2]; diff --git a/framework/resupply/functions/fn_initClient.sqf b/framework/resupply/functions/fn_initClient.sqf index a78233f..1def6f7 100644 --- a/framework/resupply/functions/fn_initClient.sqf +++ b/framework/resupply/functions/fn_initClient.sqf @@ -7,7 +7,8 @@ call FUNC(addArsenalObjectSpawnBoxActions); [ LEVEL_DEBUG, QUOTE(COMPONENT), - "postInit complete", + "initClient complete", [] ] call EFUNC(common,log); + localNamespace setVariable [QGVAR(complete), true]; \ No newline at end of file diff --git a/framework/triageIcons/functions/fn_initClient.sqf b/framework/triageIcons/functions/fn_initClient.sqf index 79b48ec..7b22f9d 100644 --- a/framework/triageIcons/functions/fn_initClient.sqf +++ b/framework/triageIcons/functions/fn_initClient.sqf @@ -6,7 +6,8 @@ GVAR(drawTargets) = []; [ LEVEL_DEBUG, QUOTE(COMPONENT), - "postInit complete", + "initClient complete", [] ] call EFUNC(common,log); + localNamespace setVariable [QGVAR(complete), true]; \ No newline at end of file diff --git a/framework/vehicleFlags/functions/fn_initClient.sqf b/framework/vehicleFlags/functions/fn_initClient.sqf index 7ebe0fd..b0d9537 100644 --- a/framework/vehicleFlags/functions/fn_initClient.sqf +++ b/framework/vehicleFlags/functions/fn_initClient.sqf @@ -1,7 +1,7 @@ -if (!hasInterface) exitWith {}; - #include "..\script_component.hpp" +if (!hasInterface) exitWith {}; + private _vehicleFlagsCfg = call FUNC(getVehicleFlagsCfg); if (!isClass _vehicleFlagsCfg) exitWith { @@ -16,94 +16,95 @@ private _flagCategoryCfgs = (_vehicleFlagsCfg >> "FlagCategories") call BIS_fnc_ private _parentClass = _x; //////////////////////////////////////////////////////////////////////// - // add CBA class event handler to add actions to vehicles after they are initialized - // all classes that inherit from the base classes will also have this applied - // an exclusion function is present for manually excluding specific classes + // create the root action //////////////////////////////////////////////////////////////////////// - [_parentClass, "InitPost", { - - - - //////////////////////////////////////////////////////////////////////// - // create the root action - //////////////////////////////////////////////////////////////////////// - private _rootActionID = "SetVehicleFlag"; - private _flagRootAction = [ - _rootActionID, // id - "Set Vehicle Flag", // displayed title - "\A3\ui_f\data\map\markers\flags\nato_ca.paa", // flag icon - {true}, // statement - { - params ["_target", "_player", "_params"]; - // _params params ["_parentActionID", "_flagCategories"]; - - // check if vehicle is excluded - private _excluded = [typeOf _target] call FUNC(isClassExcluded); - if (_excluded || !alive _target) exitWith {false}; - - true; - }, // condition - { - //////////////////////////////////////////////////////////////////////// - // create the flag category actions (with nested flag actions) - //////////////////////////////////////////////////////////////////////// - params ["_target", "_player", "_params"]; - _params params ["_rootActionID"]; - - private _vehicleFlagsCfg = call FUNC(getVehicleFlagsCfg); - if (isNull _vehicleFlagsCfg) exitWith {[]}; - private _flagCategoryCfgs = (_vehicleFlagsCfg >> "FlagCategories") call BIS_fnc_returnChildren; - - // return category child actions with individual flag actions nested as children - [_rootActionID, _flagCategoryCfgs] call FUNC(getActionsFlagCategories); - - }, // child code - [_rootActionID], // params - nil, // position - 4, // distance - [false, false, false, false, false], // other params - nil // modifier function code - ] call ace_interact_menu_fnc_createAction; - - //////////////////////////////////////////////////////////////////////// - // add root action to add flags - //////////////////////////////////////////////////////////////////////// - [ - (_this select 0), // object - 0, // action 0 or self-action 1 - ["ACE_MainActions"], // parent - _flagRootAction // action - ] call ace_interact_menu_fnc_addActionToObject; - - //////////////////////////////////////////////////////////////////////// - // add action to remove flag under the root action - //////////////////////////////////////////////////////////////////////// - // create action - private _removeFlagAction = [ - _rootActionID + "_removeflag", // id - "Remove Flag", // displayed title - "\A3\ui_f\data\map\markers\flags\nato_ca.paa", // flag icon - { - params ["_target", "_player", "_params"]; - _target forceFlagTexture ""; - }, // statement - { - params ["_target", "_player", "_params"]; - alive _target && getForcedFlagTexture _target != ""; - }, // condition - nil // child code - ] call ace_interact_menu_fnc_createAction; - - // add the action to the vehicle - // in this class event handler, this#0 will be the vehicle - [ - (_this select 0), // object - 0, // action 0 or self-action 1 - ["ACE_MainActions", _rootActionID], // parent - _removeFlagAction // action - ] call ace_interact_menu_fnc_addActionToObject; + private _rootActionID = QGVAR(SetVehicleFlagAction); + private _flagRootAction = [ + _rootActionID, // id + "Set Vehicle Flag", // displayed title + "\A3\ui_f\data\map\markers\flags\nato_ca.paa", // flag icon + {true}, // statement + { + params ["_target", "_player", "_params"]; + // _params params ["_parentActionID", "_flagCategories"]; - }, true, [], true] call CBA_fnc_addClassEventHandler; + // check if vehicle is excluded + private _excluded = [typeOf _target] call FUNC(isClassExcluded); + if (_excluded || !alive _target) exitWith {false}; + + true; + }, // condition + { + //////////////////////////////////////////////////////////////////////// + // create the flag category actions (with nested flag actions) + //////////////////////////////////////////////////////////////////////// + params ["_target", "_player", "_params"]; + _params params ["_rootActionID"]; + + private _vehicleFlagsCfg = call FUNC(getVehicleFlagsCfg); + if (isNull _vehicleFlagsCfg) exitWith {[]}; + private _flagCategoryCfgs = (_vehicleFlagsCfg >> "FlagCategories") call BIS_fnc_returnChildren; + + // return category child actions with individual flag actions nested as children + [_rootActionID, _flagCategoryCfgs] call FUNC(getActionsFlagCategories); + + }, // child code + [_rootActionID], // params + nil, // position + 4, // distance + [false, false, false, false, false], // other params + nil // modifier function code + ] call ace_interact_menu_fnc_createAction; + + //////////////////////////////////////////////////////////////////////// + // add root action to add flags + //////////////////////////////////////////////////////////////////////// + [ + _parentClass, // parent classname + 0, // action 0 or self-action 1 + ["ACE_MainActions"], // parent + _flagRootAction, // action + true // apply to child classes + ] call ace_interact_menu_fnc_addActionToClass; + + //////////////////////////////////////////////////////////////////////// + // add action to remove flag under the root action + //////////////////////////////////////////////////////////////////////// + // create action + private _removeFlagAction = [ + _rootActionID + "_removeflag", // id + "Remove Flag", // displayed title + "\A3\ui_f\data\map\markers\flags\nato_ca.paa", // flag icon + { + params ["_target", "_player", "_params"]; + _target forceFlagTexture ""; + }, // statement + { + params ["_target", "_player", "_params"]; + alive _target && getForcedFlagTexture _target != ""; + }, // condition + nil // child code + ] call ace_interact_menu_fnc_createAction; + + // add the action to the vehicle + // in this class event handler, this#0 will be the vehicle + [ + _parentClass, // parent classname + 0, // action 0 or self-action 1 + ["ACE_MainActions", _rootActionID], // parent + _removeFlagAction, // action + true // apply to child classes + ] call ace_interact_menu_fnc_addActionToClass; + } forEach _baseClassesToApplyActionsFor; +[ + LEVEL_DEBUG, + QUOTE(COMPONENT), + "initClient complete", + [] +] call EFUNC(common,log); + +localNamespace setVariable [QGVAR(complete), true]; + nil; \ No newline at end of file diff --git a/framework/vehicleFlags/functions/fn_isClassExcluded.sqf b/framework/vehicleFlags/functions/fn_isClassExcluded.sqf index 223d6ae..8c3977e 100644 --- a/framework/vehicleFlags/functions/fn_isClassExcluded.sqf +++ b/framework/vehicleFlags/functions/fn_isClassExcluded.sqf @@ -6,21 +6,30 @@ Parameter(s): 0: STRING - Classname of the vehicle to check */ - +#include "..\script_component.hpp" if (!hasInterface) exitWith {}; params [["_className", "", [""]]]; if (_className == "") exitWith {false}; -private _vehicleFlagsCfg = call milsim_vehicleFlags_fnc_getVehicleFlagsCfg; +private _vehicleFlagsCfg = call FUNC(getVehicleFlagsCfg); private _excludedVehiclesClass = (_vehicleFlagsCfg >> "ExcludedVehicles"); private _exclusionGroups = configProperties [_vehicleFlagsCfg >> "ExcludedVehicles"]; +private _isExcluded = false; { - // Check if the class doesn't have a flag proxy + // Check if the class is directly excluded private _excludedClasses = _x call BIS_fnc_getCfgDataArray; - if (_className in _excludedClasses) exitWith {true}; + if (_className in _excludedClasses) exitWith { + _isExcluded = true; + }; + { + if (_className isKindOf _x) exitWith { + _isExcluded = true; + }; + } forEach _excludedClasses; + if (_isExcluded) exitWith {}; } forEach _exclusionGroups; -false; +_isExcluded; diff --git a/framework/zeus/functions/fn_addZenModules.sqf b/framework/zeus/functions/fn_addZenModules.sqf new file mode 100644 index 0000000..41f29e0 --- /dev/null +++ b/framework/zeus/functions/fn_addZenModules.sqf @@ -0,0 +1,294 @@ +#include "..\script_component.hpp" + +if ( !hasInterface ) exitWith {}; + +// Create Resupply Box +[ + QUOTE(MODULE_CATEGORY_NAME), + "Create Resupply Box", + { + // module placement + params [["_pos", [0,0,0], [[]], 3], ["_target", objNull, [objNull]]]; + // get parent definition + private _supplyCratesCfg = call EFUNC(resupply,getSupplyCratesCfg); + // get the subclass names + private _boxTypesAvailable = _supplyCratesCfg call BIS_fnc_getCfgSubClasses; + + _boxTypesAvailable sort true; + _comboOptions = _boxTypesAvailable apply { + [ + // display name + [_supplyCratesCfg >> _x >> "displayName", "STRING", "ERROR"] call CBA_fnc_getConfigEntry, + // tooltip + [_supplyCratesCfg >> _x >> "tooltip", "STRING", "ERROR"] call CBA_fnc_getConfigEntry, + // icon + [_supplyCratesCfg >> _x >> "icon", "STRING", "ERROR"] call CBA_fnc_getConfigEntry + ] + }; + + [ // create the dialog + "Resupply Box Options", + [ + // [ "COMBO", "Box Type", [[1,2,3], [["Ammo"],["Weapons"],["Medical"]],0] ] + ["COMBO", "Box Type", [_boxTypesAvailable, _comboOptions, 0]] + ], + { + + params ["_dialog", "_args"]; + + _dialog params ["_typeOptionSelected"]; + _args params ["_pos", "_target", "_keysSorted"]; + + + private _box = [_target, _typeOptionSelected, _pos] call EFUNC(resupply,createBox); + if (isNull _box) exitWith { + ["Resupply Box", "WARNING: Failed to locate or create box!"] call BIS_fnc_curatorHint; + }; + [ + "Resupply Box", + format[ + "Created %1", + getText((call EFUNC(resupply,getSupplyCratesCfg)) >> _typeOptionSelected >> "displayName") + ] + ] call BIS_fnc_curatorHint; + }, + {}, + [_pos, _target] + ] call zen_dialog_fnc_create; + } +] call zen_custom_modules_fnc_register; + +// Manage wheels in a vehicle's ACE cargo +[ + QUOTE(MODULE_CATEGORY_NAME), + "Manage Wheels in Vehicle", + { + // module placement + params [["_pos", [0,0,0], [[]], 3], ["_target", objNull, [objNull]]]; + + if (isNull _target) exitWith { + ["Manage Wheels in Vehicle", "WARNING: No vehicle selected!"] call BIS_fnc_curatorHint; + }; + + if (_target isKindOf "CAManBase") exitWith { + ["Manage Wheels in Vehicle", "WARNING: Cannot add wheels/tracks to a person!"] call BIS_fnc_curatorHint; + }; + + if (_target isKindOf "Static") exitWith { + ["Manage Wheels in Vehicle", "WARNING: Cannot add wheels/tracks to a static object!"] call BIS_fnc_curatorHint; + }; + + // get loaded details + private _loadedItems = _target getVariable ["ace_cargo_loaded", []]; + private _loadedItemsObjects = _loadedItems select { _x isEqualType objNull }; + private _loadedItemsVirtual = _loadedItems select { _x isEqualType "" }; + private _spaceLeft = _target getVariable ["ace_cargo_space", 0]; + + private _wheels = _loadedItemsVirtual select { _x isEqualTo "ACE_Wheel" }; + _wheels append (_loadedItemsObjects select { typeOf _x isEqualTo "ACE_Wheel" }); + + + private _maxWheels = floor ((_spaceLeft + count _loadedItems) / ("ACE_Wheel" call ace_cargo_fnc_getSizeItem)); + private _currentWheels = count _wheels; + + private _comboOptions = [[], [], _currentWheels]; + for "_i" from 0 to _maxWheels do { + _comboOptions#0 pushBack _i; + _comboOptions#1 pushBack format["%1", _i]; + }; + + + [ // create the dialog + "Manage Wheels in Vehicle", + [ + // [ "COMBO", "Box Type", [[1,2,3], [["Ammo"],["Weapons"],["Medical"]],0] ] + ["TOOLBOX", "Existing Data", [ + 0, // default value + 2, // num rows + 2, // num columns + [ + format["Loaded Items: %1", count _loadedItems], + format["Space Left: %1", _spaceLeft], + format["Loaded Wheels: %1", count _wheels] + ] + ]], + ["COMBO", "Desired ACE Wheels Count", _comboOptions, true] + ], + { + + params ["_dialogValues", "_args"]; + + _dialogValues params ["_listItem", "_desiredWheelsCount"]; + _args params ["_pos", "_target", "_currentWheelsCount"]; + + // MANAGE WHEELS + if (_desiredWheelsCount > _currentWheelsCount) then { + // add wheels + private _wheelsToAdd = _desiredWheelsCount - _currentWheelsCount; + systemChat format["Adding %1 wheels...", _wheelsToAdd]; + for "_i" from 1 to _wheelsToAdd do { + if ( + ["ACE_Wheel", _target] call ace_cargo_fnc_canLoadItemIn + ) then { + ["ACE_Wheel", _target] call ace_cargo_fnc_addCargoItem; + }; + }; + }; + if (_desiredWheelsCount < _currentWheelsCount) then { + // remove wheels + private _wheelsToRemove = _currentWheelsCount - _desiredWheelsCount; + systemChat format["Removing %1 wheels...", _wheelsToRemove]; + ["ACE_Wheel", _target, _wheelsToRemove] call ace_cargo_fnc_removeCargoItem; + }; + + + // get loaded details + private _loadedItems = _target getVariable ["ace_cargo_loaded", []]; + private _loadedItemsObjects = _loadedItems select { _x isEqualType objNull }; + private _loadedItemsVirtual = _loadedItems select { _x isEqualType "" }; + private _spaceLeft = _target getVariable ["ace_cargo_space", 0]; + + private _wheels = _loadedItemsVirtual select { _x isEqualTo "ACE_Wheel" }; + _wheels append (_loadedItemsObjects select { typeOf _x isEqualTo "ACE_Wheel" }); + + + private _maxWheels = floor ((_spaceLeft + count _loadedItems) / ("ACE_Wheel" call ace_cargo_fnc_getSizeItem)); + private _currentWheels = count _wheels; + + [ + "Manage Wheels in Vehicle", + format[ + "Updated count of wheels in vehicle: %1", + _currentWheels + ] + ] call BIS_fnc_curatorHint; + true; + }, + {}, + [_pos, _target, count _wheels, count _tracks] + ] call zen_dialog_fnc_create; + } +] call zen_custom_modules_fnc_register; + + +// Manage tracks in a vehicle's ACE cargo +[ + QUOTE(MODULE_CATEGORY_NAME), + "Manage Tracks in Vehicle", + { + // module placement + params [["_pos", [0,0,0], [[]], 3], ["_target", objNull, [objNull]]]; + + if (isNull _target) exitWith { + ["Manage Tracks in Vehicle", "WARNING: No vehicle selected!"] call BIS_fnc_curatorHint; + }; + + if (_target isKindOf "CAManBase") exitWith { + ["Manage Tracks in Vehicle", "WARNING: Cannot add wheels/tracks to a person!"] call BIS_fnc_curatorHint; + }; + + if (_target isKindOf "Static") exitWith { + ["Manage Tracks in Vehicle", "WARNING: Cannot add wheels/tracks to a static object!"] call BIS_fnc_curatorHint; + }; + + // get loaded details + private _loadedItems = _target getVariable ["ace_cargo_loaded", []]; + private _loadedItemsObjects = _loadedItems select { _x isEqualType objNull }; + private _loadedItemsVirtual = _loadedItems select { _x isEqualType "" }; + private _spaceLeft = _target getVariable ["ace_cargo_space", 0]; + + private _tracks = _loadedItemsVirtual select { _x isEqualTo "ACE_Track" }; + _tracks append (_loadedItemsObjects select { typeOf _x isEqualTo "ACE_Track" }); + + private _maxTracks = floor ((_spaceLeft + count _loadedItems) / ("ACE_Track" call ace_cargo_fnc_getSizeItem)); + private _currentTracks = count _tracks; + + private _comboOptions = [[], [], _currentTracks]; + for "_i" from 0 to _maxTracks do { + _comboOptions#0 pushBack _i; + _comboOptions#1 pushBack format["%1", _i]; + }; + + [ // create the dialog + "Manage Tracks in Vehicle", + [ + // [ "COMBO", "Box Type", [[1,2,3], [["Ammo"],["Weapons"],["Medical"]],0] ] + ["TOOLBOX", "Existing Data", [ + 0, // default value + 2, // num rows + 2, // num columns + [ + format["Loaded Items: %1", count _loadedItems], + format["Space Left: %1", _spaceLeft], + format["Loaded Tracks: %1", count _tracks] + ] + ]], + ["COMBO", "Desired ACE Tracks Count", _comboOptions, true] + ], + { + + params ["_dialogValues", "_args"]; + + _dialogValues params ["_listItem", "_desiredTracksCount"]; + _args params ["_pos", "_target", "_currentTracksCount"]; + + // MANAGE TRACKS + if (_desiredTracksCount > _currentTracksCount) then { + // add tracks + private _tracksToAdd = _desiredTracksCount - _currentTracksCount; + systemChat format["Adding %1 tracks...", _tracksToAdd]; + for "_i" from 1 to _tracksToAdd do { + if ( + ["ACE_Track", _target] call ace_cargo_fnc_canLoadItemIn + ) then { + ["ACE_Track", _target] call ace_cargo_fnc_addCargoItem; + }; + }; + }; + if (_desiredTracksCount < _currentTracksCount) then { + // remove tracks + private _tracksToRemove = _currentTracksCount - _desiredTracksCount; + systemChat format["Removing %1 tracks...", _tracksToRemove]; + ["ACE_Track", _target, _tracksToRemove] call ace_cargo_fnc_removeCargoItem; + }; + + + // get loaded details + private _loadedItems = _target getVariable ["ace_cargo_loaded", []]; + private _loadedItemsObjects = _loadedItems select { _x isEqualType objNull }; + private _loadedItemsVirtual = _loadedItems select { _x isEqualType "" }; + private _spaceLeft = _target getVariable ["ace_cargo_space", 0]; + + private _tracks = _loadedItemsVirtual select { _x isEqualTo "ACE_Track" }; + _tracks append (_loadedItemsObjects select { typeOf _x isEqualTo "ACE_Track" }); + + private _maxTracks = floor ((_spaceLeft + count _loadedItems) / ("ACE_Track" call ace_cargo_fnc_getSizeItem)); + private _currentTracks = count _tracks; + + [ + "Manage Tracks in Vehicle", + format[ + "Updated count of tracks in vehicle: %1", + _currentTracks + ] + ] call BIS_fnc_curatorHint; + true; + }, + {}, + [_pos, _target, _currentTracks] + ] call zen_dialog_fnc_create; + } +] call zen_custom_modules_fnc_register; + + + + + +[ + LEVEL_INFO, + QUOTE(COMPONENT), + "ZEUS ENHANCED MODULES ADDED", + [] +] call EFUNC(common,log); + +nil; \ No newline at end of file diff --git a/framework/zeus/functions/fn_initClient.sqf b/framework/zeus/functions/fn_initClient.sqf new file mode 100644 index 0000000..28a5108 --- /dev/null +++ b/framework/zeus/functions/fn_initClient.sqf @@ -0,0 +1,14 @@ +#include "..\script_component.hpp" + +if (!hasInterface) exitWith {}; + +call FUNC(addZenModules); + +[ + LEVEL_DEBUG, + QUOTE(COMPONENT), + "postInit complete", + [] +] call EFUNC(common,log); + +localNamespace setVariable [QGVAR(complete), true]; \ No newline at end of file diff --git a/framework/zeus/script_component.hpp b/framework/zeus/script_component.hpp new file mode 100644 index 0000000..85c6e66 --- /dev/null +++ b/framework/zeus/script_component.hpp @@ -0,0 +1,3 @@ +#define COMPONENT zeus +#define COMPONENT_BEAUTIFIED Zeus Utilities +#include "../script_mod.hpp" \ No newline at end of file