diff --git a/Server Files/Changelog_25.05.2023.txt b/Server Files/Changelog_25.05.2023.txt new file mode 100644 index 000000000..d0ffd05e2 --- /dev/null +++ b/Server Files/Changelog_25.05.2023.txt @@ -0,0 +1,16 @@ +Changelog 25.05.2023 + +Server Files Updated: + +[ADDED] New HiveExt.dll compatible with MySQL 8.0.33+ +[ADDED] New Binaries: DatabaseMySql.dll, DatabasePostgre.dll, tbb.dll, tbbmalloc.dll to run the new HiveExt.dll +[FIXED] Upgrading or creating a key for a vehicle could fail if the vehicle had too many items in gear. + +Mission Files Updated: + +[FIXED] Maintain the Virtual Garage with Coins did not work properly. +[FIXED] Wooden bases with wooden walls and floors got not properly recognized as shelter. +[FIXED] Upgrading AAV_DZE to AAV_DZE1 did not work. + +Not needed on a new server: +The mission check under 'dayz_server\init\mission_check.sqf' must be updated if you are upgrading your existing server with the newest updated missionfiles. \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_1.Takistan/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_11.Chernarus/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_12.isladuala/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_13.Tavi/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_15.namalsk/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_16.Panthera2/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_17.Chernarus/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_19.FDF_Isle1_a/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_2.Chernarus_Winter/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_21.Caribou/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_22.smd_sahrani_A2/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_23.cmr_ovaron/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_24.Napf/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_25.sauerland/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_26.sauerland_winter/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_27.ruegen/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file diff --git a/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/actions/virtualGarage/player_MaintainVG.sqf b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/actions/virtualGarage/player_MaintainVG.sqf new file mode 100644 index 000000000..f72ac509f --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/actions/virtualGarage/player_MaintainVG.sqf @@ -0,0 +1,42 @@ +// Written by icomrade (https://github.com/icomrade) + +private["_itemText","_enoughMoney","_moneyInfo","_wealth","_success","_ownerPUID"]; + +closeDialog 0; + +_itemText = if (Z_SingleCurrency) then {CurrencyName} else {[vg_maintainCost,true] call z_calcCurrency}; +_enoughMoney = false; +_moneyInfo = [false, [], [], [], 0]; + +if (Z_SingleCurrency) then { + _wealth = player getVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),0]; + _enoughMoney = (_wealth >= vg_maintainCost); +} else { + Z_Selling = false; + _moneyInfo = vg_maintainCost call Z_canAfford; + _enoughMoney = _moneyInfo select 0; +}; + +_success = true; +if (vg_maintainCost > 0) then { + _success = if (Z_SingleCurrency) then {_enoughMoney} else {[player,vg_maintainCost,_moneyInfo,false,0] call Z_payDefault}; +}; + +if (!_success && _enoughMoney) exitWith {systemChat localize "STR_EPOCH_TRADE_GEAR_AND_BAG_FULL";}; + +if (_enoughMoney || vg_maintainCost < 1) then { + if (Z_SingleCurrency) then { + player setVariable [(["cashMoney","globalMoney"] select Z_persistentMoney),(_wealth - vg_maintainCost),true]; + }; + localize "STR_CL_VG_MAINTAINSUCCESS" call dayz_rollingMessages; + PVDZE_maintainGarage = if (vg_tiedToPole) then { + _plotCheck = [player,false] call FNC_find_plots; + _ownerPUID = if (_plotCheck select 1 > 0) then {(_plotCheck select 2) getVariable ["ownerPUID","0"]} else {dayz_playerUID}; + [player,_ownerPUID] + } else { + [player] + }; + publicVariableServer "PVDZE_maintainGarage"; +} else { + localize "STR_CL_VG_MAINTAINFAIL" call dayz_rollingMessages; +}; diff --git a/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/compile/fn_isSheltered.sqf b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/compile/fn_isSheltered.sqf new file mode 100644 index 000000000..e38e86203 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/compile/fn_isSheltered.sqf @@ -0,0 +1,106 @@ +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// fn_isSheltered.sqf +// +// Author: Victor the Cleaner +// Date: May 2022 +// +// Calculate how much shelter the player has and represent it as variable DZE_sheltered. +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// Raycast and perform collision check +// +/////////////////////////////////////////////////////////////////////////////////////////////////// +local _deepScan = { + + local _objects = lineIntersectsWith [_pos1, _pos2, _unit, objNull, true]; // sorted (nearest last) + local _nearest = (count _objects) - 1; // nearest object + local _idx = _this; // weight index + + scopeName "exit"; + for "_n" from _nearest to 0 step -1 do { + local _object = _objects select _n; + + call { + if (_object isKindOf "AllVehicles") exitWith {}; // exclude vehicles, zombies and other players + + local _model = _object call fn_getModelName; + + if (_model in DZE_allTrees) exitWith {}; // exclude trees + + /////////////////////////////////////////////////////////////////////////// + // + // Get object edge data + // + /////////////////////////////////////////////////////////////////////////// + + local _box = boundingBox _object; + local _edge = [_box select 1, _box select 0] call DZE_fnc_vectorDiff; + local _edgeX = _edge select 0; + local _edgeY = _edge select 1; + local _edgeZ = _edge select 2; + + local _proceed = false; + + call { + if (_edgeX > _e2 && {(_edgeY > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeY > _e2 && {(_edgeX > _e1 || {_edgeZ > _e1})}) exitWith {_proceed = true;}; + if (_edgeZ > _e2 && {(_edgeX > _e1 || {_edgeY > _e1})}) exitWith {_proceed = true;}; + }; + + if (_proceed) then { + _hitWgt set [_idx, (_hitWgt select _idx) + (_scanWgt select _idx)]; // object meets criteria + breakTo "exit"; + }; + }; + }; +}; + +/////////////////////////////////////////////////////////////////////////////////////////////////// +// +// calculate ASL vector dome +// +/////////////////////////////////////////////////////////////////////////////////////////////////// + +local _unit = _this select 0; // vehicle player +local _dir = _this select 1; // align hemisphere to building if inside +local _rad = 50; // scan radius +local _seg = 8; // initial segments +local _spin = 0; // z spin offset per arc-cycle +local _e1 = 2.5; // minimum edge length +local _e2 = 4.6; // long edge length +local _scanWgt = [1,1.5,2]; // scan weighting index +local _hitWgt = [0,0,0]; // record hit weighting +local _total = 0; // total hits, adjusted for weighting +local _pos1 = aimPos _unit; // ASL from +local _pos2 = +_pos1; // ASL to + +_pos2 set [2, (_pos2 select 2) + _rad]; // overhead pos +2 call _deepScan; // perform initial raycast +DZE_roofOverhead = (_hitWgt select 2) > 0; // valid sized object directly above + +for "_r" from 0 to 2 do { + + local _rx = 30 * _r; // aggregate x rotation above the horizon + local _arc = 360 / (_seg / (_r max 1)); // arc segments per z rotation + + for "_a" from _arc to 360 step _arc do { + local _rz = _dir + _a + _spin; // world direction with radial offset (or aligned to building) + local _pz = sin _rx; // x rotation gives z height + local _py = cos _rx; // x rotation gives y pos + local _px = _py * -(sin _rz); // z rotation gives x pos + _py = _py * (cos _rz); // z rotation gives y pos refactor + _pos2 = [_px, _py, _pz]; // unit vector (relative) + + for "_i" from 0 to 2 do { // multiply and add from/to vectors + _pos2 set [_i, ((_pos2 select _i) * _rad) + (_pos1 select _i)]; + }; + + _r call _deepScan; // perform raycast + }; + _spin = _spin + 22.5; // incremental z spin + _total = _total + (_hitWgt select _r); // hit weighting running total +}; + +DZE_sheltered = _total / 30; diff --git a/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/compile/player_upgradeVehicle.sqf b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/compile/player_upgradeVehicle.sqf new file mode 100644 index 000000000..1fe3a4554 --- /dev/null +++ b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/compile/player_upgradeVehicle.sqf @@ -0,0 +1,186 @@ +/* + DayZ Epoch Vehicle Upgrades + Made for DayZ Unleashed by [VB]AWOL please ask permission to use/edit/distrubute email vbawol@veteranbastards.com. +*/ +if (dayz_actionInProgress) exitWith {localize "STR_EPOCH_PLAYER_52" call dayz_rollingMessages;}; +dayz_actionInProgress = true; + +private ["_text","_requirementsTools","_upgradeName","_displayname","_vehicle","_proceed","_itemIn","_countIn","_missing","_missingQty","_qty","_removed","_tobe_removed_total","_textMissing","_num_removed","_removed_total","_location","_dir","_objectCharacterID","_classname","_newclassname","_upgrade","_vehicle","_finished","_temp_removed_array_mag","_temp_removed_array_wep","_notNearestPlayer","_requirementsWeapon","_requirementsMagazine"]; + +_upgrade = _this; +_vehicle = cursorTarget; + +if (isNull _vehicle || !(_vehicle isKindOf "AllVehicles") || !(alive _vehicle)) exitWith {dayz_actionInProgress = false; systemChat localize "str_cursorTargetNotFound";}; + +if (vehicle player != player) exitWith {dayz_actionInProgress = false; localize "STR_EPOCH_ACTIONS_18" call dayz_rollingMessages;}; + +_classname = typeOf _vehicle; +_displayname = getText (configFile >> "CfgVehicles" >> _classname >> "displayname"); + +if (_classname in DZE_DisableVehicleUpgrade) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_NOT_ALLOWED",_displayname] call dayz_rollingMessages;}; + +if ((player distance _vehicle) > 10) exitWith {dayz_actionInProgress = false; format [localize "STR_EPOCH_VEHUP_DISTANCE_TOO_FAR",_displayname] call dayz_rollingMessages;}; + +if (count (crew _vehicle) == 0) then { + _notNearestPlayer = _vehicle call dze_isnearest_player; + + if (local _vehicle && !_notNearestPlayer) then { + // lookup vehicle and find if any upgrades are available + _upgradeName = getText (configFile >> "CfgMagazines" >> _upgrade >> "displayname"); + + // Can be removed after a futher Epoch Update, fixes the AAV_DZE could not be upgraded due to a missing config entry + if (_classname == "AAV_DZE") then { + _upgrade = ["AAV_DZE1",["ItemToolbox","ItemCrowbar"],[],[["ItemTankORP",1],["PartEngine",6],["PartGeneric",2],["ItemScrews",2]]]; + } else { + _upgrade = getArray (configFile >> "CfgVehicles" >> _classname >> "Upgrades" >> _upgrade); + }; + + if (!isNil "_upgrade" && {(count _upgrade) > 0}) then { + closeDialog 0; + _newclassname = _upgrade select 0; + _requirementsTools = _upgrade select 1; + + if (["",_requirementsTools,"none"] call dze_requiredItemsCheck) then { + _requirementsWeapon = _upgrade select 2; + _requirementsMagazine = _upgrade select 3; + + _missingQty = 0; + _missing = ""; + + _proceed = true; + { + _itemIn = _x select 0; + _countIn = _x select 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn) } count magazines player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsMagazine; + + { + _itemIn = _x; + _countIn = 1; + _qty = { (_x == _itemIn) || (configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn) } count weapons player; + if (_qty < _countIn) exitWith { _missing = _itemIn; _missingQty = (_countIn - _qty); _proceed = false; }; + } count _requirementsWeapon; + + if (_proceed) then { + [player,(getPosATL player),20,"repair"] spawn fnc_alertZombies; + + _finished = ["Medic",1] call fn_loopAction; + if (!_finished) exitWith {}; + + if (count (crew _vehicle) > 0) exitWith {format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages;}; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + + _temp_removed_array_mag = []; + _temp_removed_array_wep = []; + _removed_total = 0; + _tobe_removed_total = 0; + + { + _removed = 0; + _itemIn = _x select 0; + _countIn = _x select 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgMagazines" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_mag set [count _temp_removed_array_mag,_x]; + }; + }; + } count magazines player; + } forEach _requirementsMagazine; + + { + _removed = 0; + _itemIn = _x; + _countIn = 1; + //diag_log format["Recipe Finish: %1 %2", _itemIn,_countIn]; + _tobe_removed_total = _tobe_removed_total + _countIn; + + { + if ((_removed < _countIn) && {(_x == _itemIn) || {configName(inheritsFrom(configFile >> "cfgWeapons" >> _x)) == _itemIn}}) then { + _num_removed = ([player,_x] call BIS_fnc_invRemove); + _removed = _removed + _num_removed; + _removed_total = _removed_total + _num_removed; + if (_num_removed >= 1) then { + _temp_removed_array_wep set [count _temp_removed_array_wep,_x]; + }; + }; + } count weapons player; + } forEach _requirementsWeapon; + + // all parts removed proceed + if (_tobe_removed_total == _removed_total) then { + call player_forceSave; + // Current charID + _objectCharacterID = _vehicle getVariable ["CharacterID","0"]; + + if (_objectCharacterID == "-1") then { + localize "str_epoch_player_50" call dayz_rollingMessages; + } else { + // Get position + _location = getposATL _vehicle; + + // Get direction + _dir = getDir _vehicle; + + localize "STR_EPOCH_VEHUP_IN_PROGRESS" call dayz_rollingMessages; + [_newclassname,objNull] call fn_waitForObject; + dze_waiting = nil; + PVDZE_veh_Upgrade = [_vehicle,[_dir,_location],_newclassname,_objectCharacterID,player,dayz_authKey]; + publicVariableServer "PVDZE_veh_Upgrade"; + + //Wait for hive to finish spawning vehicle. Prevents dupe via player queuing multiple upgrades. + waitUntil {!isNil "dze_waiting"}; + + if (dze_waiting == "fail") then { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_crafting_failed",_newclassname] call dayz_rollingMessages; + } else { + localize "STR_EPOCH_VEHUP_SUCCESS" call dayz_rollingMessages; + ["Working",0,[3,2,4,0]] call dayz_NutritionSystem; + }; + }; + } else { + {player addMagazine _x;} count _temp_removed_array_mag; + {player addWeapon _x;} count _temp_removed_array_wep; + format[localize "str_epoch_player_145",_removed_total,_tobe_removed_total] call dayz_rollingMessages; + }; + } else { + _textMissing = getText(configFile >> "CfgMagazines" >> _missing >> "displayName"); + format[localize "STR_EPOCH_ACTIONS_6",_missingQty, _textMissing] call dayz_rollingMessages; + + systemchat localize "STR_CRAFTING_NEEDED_ITEMS"; + + if (count _requirementsMagazine > 0) then { + { + _text = getText(configFile >> "CfgMagazines" >> (_x select 0) >> "displayName"); + systemchat format ["%2x %1",_text,(_x select 1)]; + } count _requirementsMagazine; + }; + if (count _requirementsWeapon > 0) then { + { + _text = getText(configFile >> "CfgWeapons" >> _x >> "displayName"); + systemchat format ["1x %1",_text]; + + } count _requirementsWeapon; + }; + }; + }; + } else { + format [localize "STR_EPOCH_VEHUP_NO_UPGRADE_FOR_VEHICLE",_upgradeName,_displayname] call dayz_rollingMessages; + }; + } else { + localize "str_epoch_player_245" call dayz_rollingMessages; + }; +} else { + format [localize "STR_CL_LOG_FAIL_PLAYER",_displayname] call dayz_rollingMessages; +}; + +dayz_actionInProgress = false; diff --git a/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/init/compiles.sqf b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/init/compiles.sqf index 42c823ad1..8a3bb5e55 100644 --- a/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/init/compiles.sqf +++ b/Server Files/MPMissions/DayZ_Epoch_7.Lingor/dayz_code/init/compiles.sqf @@ -5,4 +5,18 @@ if (isServer) then { if (!isDedicated) then { //Add your custom or override functions here //fnc_usec_selfActions = compile preprocessFileLineNumbers "dayz_code\compile\fn_selfActions.sqf"; + + // All fixes down below can be removed in a future Epoch Update + + // Fix Wooden bases with wooden walls and floors got not properly recognized as shelter. + fnc_issheltered = compile preprocessFileLineNumbers "dayz_code\compile\fn_isSheltered.sqf"; + + // Fix upgrading AAV_DZE to AAV_DZE1 did not work, only needed if you are using the AAV_DZE + player_upgradeVehicle = compile preprocessFileLineNumbers "dayz_code\compile\player_upgradeVehicle.sqf"; + + // Fix Maintain the Virtual Garage with Coins does not work properly + if (DZE_Virtual_Garage) then { + Player_MaintainVG = compile preprocessFileLineNumbers "dayz_code\actions\virtualGarage\player_MaintainVG.sqf"; + }; + }; \ No newline at end of file