mirror of
https://github.com/acemod/ACE3.git
synced 2024-08-30 18:23:18 +00:00
Repair - Make Full Repair Time dependent on vehicle damage (#8417)
* add variable full repair time * enable compile cache * Fix stupid * whoops * incremental full repair * cleanup function header * ignore hitpoints inFullRepairProgress * fix getHitPointsToIgnore * final cleanup * don't show repair hint while doing full repair * make this all work * fix stupid put this back in place * Add setting for speedup when near repair facility/vehicle enable compile cache * refactor near repair facility/vehicle checks * remove skipping hint from do_repair better for feedback this way * git diff stuff * use functions directly in ACE_Repair.hpp * add check for vehicle proximity * add a new line * switch to multiply by setting instead * speed boost settings, remove exit addRepairActions * stringtable * remove speed boost settings * fix things, add forceDisplayName * name in function header * fix TRACE * add animation looping * remove systemChat Co-authored-by: Filip Maciejewski <veteran29@users.noreply.github.com> * add time coefficient setting * move to repair category * time coefficient max and default values --------- Co-authored-by: Salluci <69561145+Salluci@users.noreply.github.com> Co-authored-by: Filip Maciejewski <veteran29@users.noreply.github.com>
This commit is contained in:
parent
50430e47ef
commit
04e41a4d5a
@ -3,10 +3,11 @@ class ACE_Repair {
|
||||
class ReplaceWheel {
|
||||
displayName = CSTRING(ReplaceWheel);
|
||||
displayNameProgress = CSTRING(ReplacingWheel);
|
||||
forceDisplayName = 0;
|
||||
|
||||
repairLocations[] = {"All"};
|
||||
requiredEngineer = QGVAR(engineerSetting_Wheel);
|
||||
repairingTime = 10;
|
||||
repairingTime = QGVAR(wheelChangeTime);
|
||||
repairingTimeSelfCoef = 1;
|
||||
items = QGVAR(wheelRepairRequiredItems);
|
||||
condition = QFUNC(canReplaceWheel);
|
||||
@ -21,6 +22,7 @@ class ACE_Repair {
|
||||
animationCallerProne = "Acts_carFixingWheel";
|
||||
animationCallerSelf = "Acts_carFixingWheel";
|
||||
animationCallerSelfProne = "Acts_carFixingWheel";
|
||||
loopAnimation = 0;
|
||||
litter[] = {};
|
||||
};
|
||||
class RemoveWheel: ReplaceWheel {
|
||||
@ -46,7 +48,7 @@ class ACE_Repair {
|
||||
displayNameProgress = CSTRING(RepairingHitPoint);
|
||||
condition = QFUNC(canMiscRepair);
|
||||
requiredEngineer = QGVAR(engineerSetting_Repair);
|
||||
repairingTime = 15;
|
||||
repairingTime = QGVAR(miscRepairTime);
|
||||
callbackSuccess = QFUNC(doRepair);
|
||||
items = QGVAR(miscRepairRequiredItems);
|
||||
itemConsumed = QGVAR(consumeItem_ToolKit);
|
||||
@ -80,11 +82,14 @@ class ACE_Repair {
|
||||
class FullRepair: MiscRepair {
|
||||
displayName = CSTRING(fullRepair);
|
||||
displayNameProgress = CSTRING(fullyRepairing);
|
||||
forceDisplayName = 1;
|
||||
loopAnimation = 1;
|
||||
requiredEngineer = QGVAR(engineerSetting_fullRepair);
|
||||
repairLocations[] = {QGVAR(fullRepairLocation)};
|
||||
repairingTime = 30;
|
||||
condition = "-1 != ((getAllHitPointsDamage _target param [2,[]]) findIf {_x > 0})";
|
||||
repairingTime = QFUNC(getFullRepairTime);
|
||||
condition = "((getAllHitPointsDamage _target) select 2) findIf {_x > 0} != -1";
|
||||
callbackSuccess = QFUNC(doFullRepair);
|
||||
callbackProgress = QFUNC(fullRepairProgress);
|
||||
items = QGVAR(fullRepairRequiredItems);
|
||||
itemConsumed = QGVAR(consumeItem_ToolKit);
|
||||
};
|
||||
|
@ -17,8 +17,11 @@ PREP(doRepair);
|
||||
PREP(doRepairTrack);
|
||||
PREP(doReplaceTrack);
|
||||
PREP(doReplaceWheel);
|
||||
PREP(fullRepairProgress);
|
||||
PREP(getClaimObjects);
|
||||
PREP(getFullRepairTime);
|
||||
PREP(getHitPointString);
|
||||
PREP(getHitPointsToIgnore);
|
||||
PREP(getPatchWheelTime);
|
||||
PREP(getPostRepairDamage);
|
||||
PREP(getRepairItems);
|
||||
|
@ -25,6 +25,9 @@ TRACE_2("addRepairActions", _vehicle,_type);
|
||||
private _initializedClasses = GETMVAR(GVAR(initializedClasses),[]);
|
||||
if (_type in _initializedClasses) exitWith {};
|
||||
|
||||
// get hitPoints to ignore
|
||||
private _hitPointsToIgnore = [_vehicle] call FUNC(getHitPointsToIgnore);
|
||||
|
||||
// get all hitpoints and selections
|
||||
(getAllHitPointsDamage _vehicle) params [["_hitPoints", []], ["_hitSelections", []]]; // Since 1.82 these are all lower case
|
||||
|
||||
@ -40,8 +43,6 @@ private _icon = ["a3\ui_f\data\igui\cfg\actions\repair_ca.paa", "#FFFFFF"];
|
||||
private _vehCfg = configOf _vehicle;
|
||||
// Custom position can be defined via config for associated hitpoint
|
||||
private _hitpointPositions = getArray (_vehCfg >> QGVAR(hitpointPositions));
|
||||
// Associated hitpoints can be grouped via config to produce a single repair action
|
||||
private _hitpointGroups = getArray (_vehCfg >> QGVAR(hitpointGroups));
|
||||
// Get turret paths
|
||||
private _turretPaths = ((fullCrew [_vehicle, "gunner", true]) + (fullCrew [_vehicle, "commander", true])) apply {_x # 3};
|
||||
|
||||
@ -88,59 +89,32 @@ private _turretPaths = ((fullCrew [_vehicle, "gunner", true]) + (fullCrew [_vehi
|
||||
|
||||
_processedSelections pushBack _selection;
|
||||
} else {
|
||||
// Empty hitpoints don't contain enough information
|
||||
if (_hitpoint isEqualTo "") exitWith { TRACE_3("Skipping Empty Hit",_hitpoint,_forEachIndex,_selection); };
|
||||
// Ignore glass hitpoints
|
||||
if ((_hitpoint find "glass") != -1) exitWith { TRACE_3("Skipping Glass",_hitpoint,_forEachIndex,_selection); };
|
||||
// Ignore hitpoints starting with # (seems to be lights)
|
||||
if ((_hitpoint select [0,1]) == "#") exitWith { TRACE_3("Skipping # hit",_hitpoint,_forEachIndex,_selection); };
|
||||
// Ignore ERA/Slat armor (vanilla uses hitera_/hitslat_, pre-1.82 RHS uses era_)
|
||||
// ToDo: see how community utilizes new armor system, could also check getText (_hitpointConfig >> "simulation")
|
||||
if (((_hitpoint select [0,7]) == "hitera_") || {(_hitpoint select [0,8]) == "hitslat_"} || {(_hitpoint select [0,4]) == "era_"}) exitWith { TRACE_3("Skipping ERA/SLAT",_hitpoint,_forEachIndex,_selection); };
|
||||
// Skip ignored hitpoints
|
||||
if (_hitpoint in _hitPointsToIgnore) exitWith {
|
||||
TRACE_3("Skipping ignored hitpoint",_hitpoint,_forEachIndex,_selection);
|
||||
};
|
||||
|
||||
// Some hitpoints do not have a selection but do have an armorComponent value (seems to mainly be RHS)
|
||||
// Ref https://community.bistudio.com/wiki/Arma_3_Damage_Enhancement
|
||||
// this code won't support identically named hitpoints (e.g. commander turret: Duplicate HitPoint name 'HitTurret')
|
||||
private _armorComponent = "";
|
||||
if (_selection == "") then {
|
||||
private _hitpointsCfg = "configName _x == _hitpoint" configClasses (_vehCfg >> "HitPoints");
|
||||
if (_hitpointsCfg isNotEqualTo []) then {
|
||||
_armorComponent = getText (_hitpointsCfg # 0 >> "armorComponent");
|
||||
};
|
||||
if (_armorComponent == "") then {
|
||||
{
|
||||
private _turretHitpointCfg = ([_vehCfg, _x] call CBA_fnc_getTurret) >> "HitPoints";
|
||||
private _hitpointsCfg = "configName _x == _hitpoint" configClasses _turretHitpointCfg;
|
||||
if (_hitpointsCfg isNotEqualTo []) exitWith {
|
||||
TRACE_2("turret hitpoint configFound",_hitpoint,_x);
|
||||
// only do turret hitpoints or stuff linked to visuals for now or we apparently get some weird stuff
|
||||
if ((_hitpoint in ["hitturret", "hitgun"]) || {(getNumber (_hitpointsCfg # 0 >> "isGun")) == 1} || {(getNumber (_hitpointsCfg # 0 >> "isTurret")) == 1} || {(getText (_hitpointsCfg # 0 >> "visual")) != ""}) then {
|
||||
_armorComponent = getText (_hitpointsCfg # 0 >> "armorComponent");
|
||||
};
|
||||
};
|
||||
} forEach _turretPaths;
|
||||
if (_armorComponent == "") then {
|
||||
private _hitpointsCfg = "configName _x == _hitpoint" configClasses (_vehCfg >> "HitPoints");
|
||||
if ((getText (_hitpointsCfg # 0 >> "visual")) != "") then {
|
||||
_armorComponent = getText (_hitpointsCfg # 0 >> "armorComponent");
|
||||
};
|
||||
};
|
||||
if (_armorComponent != "") then { INFO_3("%1: %2 no selection: using armorComponent %3",_type,_hitpoint,_armorComponent); };
|
||||
};
|
||||
if ((_selection == "") && {_armorComponent == ""}) exitWith { TRACE_3("Skipping no selection OR armor component",_hitpoint,_forEachIndex,_selection); };
|
||||
|
||||
|
||||
//Depends hitpoints shouldn't be modified directly (will be normalized)
|
||||
// Biki: Clearing 'depends' in case of inheritance cannot be an empty string (rpt warnings), but rather a "0" value.
|
||||
if (!((getText (_vehCfg >> "HitPoints" >> _hitpoint >> "depends")) in ["", "0"])) exitWith {
|
||||
TRACE_3("Skip Depends",_hitpoint,_forEachIndex,_selection);
|
||||
};
|
||||
|
||||
private _childHitPoint = false;
|
||||
{
|
||||
{
|
||||
if (_hitpoint == _x) exitWith {
|
||||
_childHitPoint = true;
|
||||
};
|
||||
} forEach (_x select 1);
|
||||
} forEach _hitpointGroups;
|
||||
// If the current selection is associated with a child hitpoint, then skip
|
||||
if (_childHitPoint) exitWith { TRACE_3("childHitpoint",_hitpoint,_forEachIndex,_selection); };
|
||||
|
||||
// Find the action position
|
||||
private _position = compile format ["_target selectionPosition ['%1', 'HitPoints'];", _selection];
|
||||
|
@ -7,6 +7,7 @@
|
||||
* 0: Unit that does the repairing <OBJECT>
|
||||
* 1: Vehicle to repair <OBJECT>
|
||||
* 2: Selected hitpointIndex <NUMBER>
|
||||
* 3: Repair action classname <STRING>
|
||||
*
|
||||
* Return Value:
|
||||
* None
|
||||
@ -17,10 +18,11 @@
|
||||
* Public: No
|
||||
*/
|
||||
|
||||
params ["_unit", "_vehicle", "_hitPointIndex"];
|
||||
TRACE_3("params",_unit,_vehicle,_hitPointIndex);
|
||||
params ["_unit", "_vehicle", "_hitPointIndex", "_action"];
|
||||
TRACE_4("params",_unit,_vehicle,_hitPointIndex,_action);
|
||||
|
||||
private _postRepairDamageMin = [_unit] call FUNC(getPostRepairDamage);
|
||||
// override minimum damage if doing full repair
|
||||
private _postRepairDamageMin = [_unit, _action isEqualTo "fullRepair"] call FUNC(getPostRepairDamage);
|
||||
|
||||
(getAllHitPointsDamage _vehicle) params ["_allHitPoints"];
|
||||
private _hitPointClassname = _allHitPoints select _hitPointIndex;
|
||||
|
50
addons/repair/functions/fnc_fullRepairProgress.sqf
Normal file
50
addons/repair/functions/fnc_fullRepairProgress.sqf
Normal file
@ -0,0 +1,50 @@
|
||||
#include "script_component.hpp"
|
||||
/*
|
||||
* Author: LinkIsGrim
|
||||
* Handles full repair by periodically repairing damaged hitpoints.
|
||||
*
|
||||
* Arguments:
|
||||
* 0: Arguments <ARRAY>
|
||||
* 0: Engineer <OBJECT>
|
||||
* 1: Vehicle <OBJECT>
|
||||
* 2: Hitpoint <STRING> (unused)
|
||||
* 3: Repair action classname <STRING>
|
||||
* 1: Elapsed Time <NUMBER>
|
||||
* 2: Total Time <NUMBER>
|
||||
*
|
||||
* Return Value:
|
||||
* Continue Repair <BOOL>
|
||||
*
|
||||
* Example:
|
||||
* [[objNull, player], 5, 10] call ace_repair_fnc_fullRepairProgress
|
||||
*
|
||||
* Public: No
|
||||
*/
|
||||
|
||||
params ["_args", "_elapsedTime", "_totalTime"];
|
||||
_args params ["_engineer", "_vehicle", "", "_action"];
|
||||
|
||||
if !((alive _vehicle) && {(abs speed _vehicle) < 1}) exitWith {false}; // make sure vehicle doesn't drive off
|
||||
|
||||
// Not enough time has elapsed to repair a hitpoint
|
||||
if (_totalTime - _elapsedTime > ([_engineer, _vehicle] call FUNC(getFullRepairTime)) - (GVAR(miscRepairTime) * GVAR(timeCoefficientFullRepair))) exitWith {true};
|
||||
|
||||
private _allHitPointsDamage = getAllHitPointsDamage _vehicle;
|
||||
_allHitPointsDamage params ["_hitPoints", "", "_damageValues"];
|
||||
|
||||
private _hitPointsToIgnore = [_vehicle] call FUNC(getHitPointsToIgnore);
|
||||
|
||||
private _firstDamagedIndex = {
|
||||
private _hitPoint = _hitPoints select _forEachIndex;
|
||||
if (_x > 0 && {!(_hitPoint in _hitPointsToIgnore)}) exitWith {_forEachIndex};
|
||||
-1
|
||||
} forEach _damageValues;
|
||||
|
||||
// Stop repairing if there are no more damaged hitpoints
|
||||
// callBackSuccess to FUNC(doFullRepair) for ignored hitpoints
|
||||
if (_firstDamagedIndex == -1) exitWith {true};
|
||||
|
||||
// Repair the first damaged hitpoint
|
||||
[_engineer, _vehicle, _firstDamagedIndex, _action] call FUNC(doRepair);
|
||||
|
||||
true
|
42
addons/repair/functions/fnc_getFullRepairTime.sqf
Normal file
42
addons/repair/functions/fnc_getFullRepairTime.sqf
Normal file
@ -0,0 +1,42 @@
|
||||
#include "script_component.hpp"
|
||||
/*
|
||||
* Author: LinkIsGrim
|
||||
* Calculates the Full Repair time based on the amount of hitpoints to repair
|
||||
*
|
||||
* Arguments:
|
||||
* 0: Engineer <OBJECT>
|
||||
* 1: Vehicle <OBJECT>
|
||||
*
|
||||
* Return Value:
|
||||
* Repair Time <NUMBER>
|
||||
*
|
||||
* Example:
|
||||
* [player, vehicle] call ace_repair_fnc_getFullRepairTime
|
||||
*
|
||||
* Public: No
|
||||
*/
|
||||
|
||||
params ["_engineer", "_vehicle"];
|
||||
|
||||
private _allHitPointsDamage = getAllHitPointsDamage _vehicle;
|
||||
_allHitPointsDamage params ["_hitPoints", "", "_damageValues"];
|
||||
|
||||
private _hitPointsToIgnore = [_vehicle] call FUNC(getHitPointsToIgnore);
|
||||
|
||||
private _repairsNeeded = 0;
|
||||
private _doExtraRepair = false;
|
||||
{
|
||||
if (_x <= 0) then {continue}; // skip hitpoints that don't need repairs
|
||||
private _hitPoint = _hitPoints select _forEachIndex;
|
||||
if (_hitPoint in _hitPointsToIgnore) then { // only add extra repair for ignore hitpoints if they're damaged
|
||||
_doExtraRepair = true;
|
||||
continue
|
||||
};
|
||||
_repairsNeeded = _repairsNeeded + ceil (_x / 0.5); // repair is capped at 0.5 in FUNC(doRepair)
|
||||
} forEach _damageValues;
|
||||
|
||||
if (_doExtraRepair) then {
|
||||
_repairsNeeded = _repairsNeeded + 1;
|
||||
};
|
||||
|
||||
_repairsNeeded * GVAR(miscRepairTime) * GVAR(timeCoefficientFullRepair) // return
|
142
addons/repair/functions/fnc_getHitPointsToIgnore.sqf
Normal file
142
addons/repair/functions/fnc_getHitPointsToIgnore.sqf
Normal file
@ -0,0 +1,142 @@
|
||||
#include "script_component.hpp"
|
||||
/*
|
||||
* Author: commy2, kymckay, LinkIsGrim
|
||||
* Get list of vehicle hitpoints to ignore
|
||||
*
|
||||
* Arguments:
|
||||
* 0: Vehicle <OBJECT>
|
||||
*
|
||||
* Return Value:
|
||||
* HitPoints to ignore <ARRAY>
|
||||
*
|
||||
* Example:
|
||||
* [vehicle] call ace_repair_fnc_getHitpointsToIgnore
|
||||
*
|
||||
* Public: No
|
||||
*/
|
||||
|
||||
params ["_vehicle"];
|
||||
|
||||
private _type = typeOf _vehicle;
|
||||
TRACE_2("getHitPointsToIgnore", _vehicle,_type);
|
||||
private _initializedClasses = missionNamespace getVariable [QGVAR(hitPointsToIgnoreInitializedClasses), createHashMap];
|
||||
if (_type in _initializedClasses) exitWith {_initializedClasses get _type};
|
||||
|
||||
private _vehCfg = configOf _vehicle;
|
||||
private _hitpointGroups = getArray (_vehCfg >> QGVAR(hitpointGroups));
|
||||
private _turretPaths = ((fullCrew [_vehicle, "gunner", true]) + (fullCrew [_vehicle, "commander", true])) apply {_x # 3};
|
||||
|
||||
(getAllHitPointsDamage _vehicle) params [["_hitPoints", []], ["_hitSelections", []]];
|
||||
// get hitpoints of wheels with their selections
|
||||
([_vehicle] call FUNC(getWheelHitPointsWithSelections)) params ["_wheelHitPoints", "_wheelHitSelections"];
|
||||
|
||||
private _hitPointsToIgnore = [""]; // always ignore empty hitpoints
|
||||
private _processedSelections = [];
|
||||
|
||||
{
|
||||
private _selection = _x;
|
||||
private _hitpoint = toLower (_hitPoints select _forEachIndex);
|
||||
private _isWheelOrTrack = _selection in _wheelHitSelections || {_hitpoint in _wheelHitPoints} || {_hitpoint in TRACK_HITPOINTS};
|
||||
|
||||
if (_hitpoint isEqualTo "") then { // skip empty hitpoint
|
||||
continue
|
||||
};
|
||||
|
||||
if (_isWheelOrTrack && {_selection in _processedSelections || {_selection isEqualTo ""}}) then { // skip duplicate or empty selection wheel/track
|
||||
TRACE_3("Skipping duplicate Wheel/Track or empty selection",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping duplicate wheel, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
if ("glass" in _hitpoint) then { // skip glass
|
||||
TRACE_3("Skipping glass",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping glass, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
if (_hitpoint select [0,1] isEqualTo "#" || {_hitpoint select [0,9] isEqualTo "hit_light"}) then { // skip lights
|
||||
TRACE_3("Skipping light",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping light, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
if (_hitpoint select [0,7] isEqualTo "hitera_" || {_hitpoint select [0,8] isEqualTo "hitslat_"} || {_hitpoint select [0,4] isEqualTo "era_"}) then { // skip era/slat
|
||||
TRACE_3("Skipping ERA/Slat HitPoint",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping ERA/SLAT, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
private _armorComponent = "";
|
||||
if (_selection == "") then { // some hitpoints have empty selection but defined armor component (mostly RHS)
|
||||
{
|
||||
private _turretHitpointCfg = ([_vehCfg, _x] call CBA_fnc_getTurret) >> "HitPoints";
|
||||
private _hitpointsCfg = "configName _x == _hitpoint" configClasses _turretHitpointCfg;
|
||||
if (_hitpointsCfg isNotEqualTo []) exitWith {
|
||||
TRACE_2("turret hitpoint configFound",_hitpoint,_x);
|
||||
// only do turret hitpoints and stuff linked to visuals
|
||||
if ((_hitpoint in ["hitturret", "hitgun"]) || {(getNumber (_hitpointsCfg # 0 >> "isGun")) == 1} || {(getNumber (_hitpointsCfg # 0 >> "isTurret")) == 1} || {(getText (_hitpointsCfg # 0 >> "visual")) != ""}) then {
|
||||
_armorComponent = getText (_hitpointsCfg # 0 >> "armorComponent");
|
||||
};
|
||||
};
|
||||
} forEach _turretPaths;
|
||||
if (_armorComponent == "") then {
|
||||
private _hitpointsCfg = "configName _x == _hitpoint" configClasses (_vehCfg >> "HitPoints");
|
||||
if (_hitpointsCfg isNotEqualTo [] && {(getText (_hitpointsCfg # 0 >> "visual")) != ""}) then {
|
||||
_armorComponent = getText (_hitpointsCfg # 0 >> "armorComponent");
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
if ((_selection == "") && {_armorComponent == ""}) then {
|
||||
TRACE_3("Skipping no selection OR armor component",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping no selection OR armor component, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
if (!(getText (_vehCfg >> "HitPoints" >> _hitpoint >> "depends") in ["", "0"])) then { // skip depends hitpoints, should be normalized by engine
|
||||
TRACE_3("Skipping depends hitpoint",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping depends hitpoint, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
if ((_hitpointGroups findIf {(_x select 1) == _hitpoint}) != -1) then { // skip child hitpoints
|
||||
TRACE_3("Skipping child hitpoint",_hitpoint,_forEachIndex,_selection);
|
||||
/*#ifdef DEBUG_MODE_FULL
|
||||
systemChat format ["Skipping child hitpoint, hitpoint %1, index %2, selection %3", _hitpoint, _forEachIndex, _selection];
|
||||
#endif*/
|
||||
_hitPointsToIgnore pushBackUnique _hitpoint;
|
||||
_processedSelections pushBack _selection;
|
||||
continue
|
||||
};
|
||||
|
||||
_processedSelections pushBack _selection;
|
||||
} forEach _hitSelections;
|
||||
|
||||
_initializedClasses set [_type, _hitPointsToIgnore];
|
||||
missionNamespace setVariable [QGVAR(hitPointsToIgnoreInitializedClasses), _initializedClasses];
|
||||
|
||||
_hitPointsToIgnore
|
@ -5,6 +5,7 @@
|
||||
*
|
||||
* Arguments:
|
||||
* 0: Unit that does the repairing <OBJECT>
|
||||
* 1: Override for full repair <BOOL> (default: false)
|
||||
*
|
||||
* Return Value:
|
||||
* 0: Repair Damage Threshold <NUMBER>
|
||||
@ -15,11 +16,11 @@
|
||||
* Public: No
|
||||
*/
|
||||
|
||||
params ["_unit"];
|
||||
TRACE_1("params",_unit);
|
||||
params ["_unit", ["_override", false]];
|
||||
TRACE_2("params",_unit,_override);
|
||||
|
||||
//If in facility or near vehicle then complete repair of hitpoint:
|
||||
if (([_unit] call FUNC(isInRepairFacility) || {[_unit] call FUNC(isNearRepairVehicle)})) exitWith {0};
|
||||
//If in facility, near vehicle, or doing full repair then complete repair of hitpoint:
|
||||
if ((_override || {[_unit] call FUNC(isInRepairFacility)} || {[_unit] call FUNC(isNearRepairVehicle)})) exitWith {0};
|
||||
|
||||
private _class = _unit getVariable ["ACE_IsEngineer", getNumber (configOf _unit >> "engineer")];
|
||||
//If advanced or more qualified than min, then use engineer threshold:
|
||||
|
@ -15,28 +15,15 @@
|
||||
* Public: Yes
|
||||
*/
|
||||
|
||||
#define CHECK_OBJECTS(var) ((var) findIf {(_x getVariable ["ACE_isRepairFacility", getNumber (configOf _x >> QGVAR(canRepair))] > 0) && {!(_x isKindOf "AllVehicles")} && {alive _x}} != -1)
|
||||
|
||||
params [["_object", objNull, [objNull]]];
|
||||
TRACE_1("params",_object);
|
||||
|
||||
private _position = getPosASL _object;
|
||||
private _isInBuilding = false;
|
||||
|
||||
private _checkObject = {
|
||||
if (
|
||||
_x getVariable ["ACE_isRepairFacility", getNumber (configOf _x >> QGVAR(canRepair))] > 0
|
||||
&& {!(_x isKindOf "AllVehicles")} // check if it's not repair vehicle
|
||||
&& {alive _x}
|
||||
) exitWith {
|
||||
_isInBuilding = true;
|
||||
};
|
||||
private _fnc_check = {
|
||||
private _position = _object modelToWorldVisual [0, 0, eyePos _object select 2];
|
||||
CHECK_OBJECTS(lineIntersectsWith [ARR_3(_position, _position vectorAdd [ARR_3(0, 0, 10)], _object)]) || {CHECK_OBJECTS(_object nearObjects 7.5)}
|
||||
};
|
||||
|
||||
private _objects = (lineIntersectsWith [_object modelToWorldVisual [0, 0, (_position select 2)], _object modelToWorldVisual [0, 0, (_position select 2) +10], _object]);
|
||||
_checkObject forEach _objects;
|
||||
|
||||
if (_isInBuilding) exitWith {true};
|
||||
|
||||
_objects = _object nearObjects 7.5;
|
||||
_checkObject forEach _objects;
|
||||
|
||||
_isInBuilding
|
||||
[[], _fnc_check, _object, QGVAR(inRepairFacilityCache), IN_REPAIR_FACILITY_CACHE_EXPIRY] call EFUNC(common,cachedCall);
|
||||
|
@ -15,14 +15,14 @@
|
||||
* Public: Yes
|
||||
*/
|
||||
|
||||
#define CHECK_OBJECTS(var) ((var) findIf {alive _x && {[_x] call FUNC(isRepairVehicle)}} != -1)
|
||||
|
||||
params ["_unit"];
|
||||
TRACE_1("params",_unit);
|
||||
|
||||
private _fnc_check = {
|
||||
private _nearObjects = nearestObjects [_unit, ["Air", "LandVehicle", "Slingload_base_F"], 20];
|
||||
CHECK_OBJECTS(_nearObjects)
|
||||
};
|
||||
|
||||
private _return = false;
|
||||
{
|
||||
if (alive _x && {[_x] call FUNC(isRepairVehicle)}) exitWith {_return = true;};
|
||||
} forEach _nearObjects;
|
||||
|
||||
_return;
|
||||
[[], _fnc_check, _unit, QGVAR(nearRepairVehicleCache), NEAR_REPAIR_VEHICLE_CACHE_EXPIRY] call EFUNC(common,cachedCall);
|
||||
|
@ -148,6 +148,7 @@ if (_callbackProgress == "") then {
|
||||
|
||||
// Player Animation
|
||||
private _callerAnim = [getText (_config >> "animationCaller"), getText (_config >> "animationCallerProne")] select (stance _caller == "PRONE");
|
||||
private _loopAnim = (getNumber (_config >> "loopAnimation")) isEqualTo 1;
|
||||
_caller setVariable [QGVAR(selectedWeaponOnrepair), currentWeapon _caller];
|
||||
|
||||
// Cannot use secondairy weapon for animation
|
||||
@ -171,10 +172,27 @@ if (vehicle _caller == _caller && {_callerAnim != ""}) then {
|
||||
} else {
|
||||
_caller setVariable [QGVAR(repairPrevAnimCaller), animationState _caller];
|
||||
};
|
||||
_caller setVariable [QGVAR(repairCurrentAnimCaller), toLower _callerAnim];
|
||||
[_caller, _callerAnim] call EFUNC(common,doAnimation);
|
||||
};
|
||||
};
|
||||
|
||||
if (_loopAnim) then {
|
||||
private _animDoneEh = _caller addEventHandler ["AnimDone", {
|
||||
params ["_caller", "_anim"];
|
||||
if (_anim isEqualTo (_caller getVariable [QGVAR(repairCurrentAnimCaller), ""])) then {
|
||||
[{
|
||||
params ["_caller", "_anim"];
|
||||
if !(isNil {_caller getVariable QGVAR(repairCurrentAnimCaller)}) then {
|
||||
TRACE_2("loop",_caller,_anim);
|
||||
_this call EFUNC(common,doAnimation)
|
||||
};
|
||||
}, [_caller, _anim], 2.5] call CBA_fnc_waitAndExecute;
|
||||
};
|
||||
}];
|
||||
_caller setVariable [QGVAR(repairLoopAnimEh), _animDoneEh];
|
||||
};
|
||||
|
||||
private _soundPosition = _caller modelToWorldVisualWorld (_caller selectionPosition "RightHand");
|
||||
["Acts_carFixingWheel", _soundPosition, nil, 50] call EFUNC(common,playConfigSound3D);
|
||||
|
||||
@ -213,7 +231,10 @@ private _hitPointClassname = if (_hitPoint isEqualType "") then {
|
||||
};
|
||||
private _processText = getText (_config >> "displayNameProgress");
|
||||
private _backupText = format [localize LSTRING(RepairingHitPoint), _hitPointClassname];
|
||||
([_hitPointClassname, _processText, _backupText] call FUNC(getHitPointString)) params ["_text"];
|
||||
private _text = _processText;
|
||||
if (getNumber (_config >> "forceDisplayName") isNotEqualTo 1) then {
|
||||
_text = ([_hitPointClassname, _processText, _backupText] call FUNC(getHitPointString)) select 0;
|
||||
};
|
||||
|
||||
TRACE_4("display",_hitPoint,_hitPointClassname,_processText,_text);
|
||||
|
||||
|
@ -29,9 +29,13 @@ TRACE_5("params",_caller,_target,_selectionName,_className,_usersOfItems);
|
||||
if (primaryWeapon _caller == "ACE_FakePrimaryWeapon") then {
|
||||
_caller removeWeapon "ACE_FakePrimaryWeapon";
|
||||
};
|
||||
|
||||
_caller removeEventHandler ["AnimDone", _caller getVariable [QGVAR(repairLoopAnimEh), -1]];
|
||||
_caller setVariable [QGVAR(repairLoopAnimEh), nil];
|
||||
if (vehicle _caller == _caller && {!(_caller call EFUNC(common,isSwimming))}) then {
|
||||
[_caller, _caller getVariable [QGVAR(repairPrevAnimCaller), ""], 2] call EFUNC(common,doAnimation);
|
||||
};
|
||||
_caller setVariable [QGVAR(repairCurrentAnimCaller), nil];
|
||||
_caller setVariable [QGVAR(repairPrevAnimCaller), nil];
|
||||
|
||||
private _weaponSelect = (_caller getVariable [QGVAR(selectedWeaponOnrepair), ""]);
|
||||
|
@ -29,9 +29,13 @@ TRACE_4("params",_caller,_target,_selectionName,_className);
|
||||
if (primaryWeapon _caller == "ACE_FakePrimaryWeapon") then {
|
||||
_caller removeWeapon "ACE_FakePrimaryWeapon";
|
||||
};
|
||||
|
||||
_caller removeEventHandler ["AnimDone", _caller getVariable [QGVAR(repairLoopAnimEh), -1]];
|
||||
_caller setVariable [QGVAR(repairLoopAnimEh), nil];
|
||||
if (vehicle _caller == _caller && {!(_caller call EFUNC(common,isSwimming))}) then {
|
||||
[_caller, _caller getVariable [QGVAR(repairPrevAnimCaller), ""], 2] call EFUNC(common,doAnimation);
|
||||
};
|
||||
_caller setVariable [QGVAR(repairCurrentAnimCaller), nil];
|
||||
_caller setVariable [QGVAR(repairPrevAnimCaller), nil];
|
||||
|
||||
private _weaponSelect = (_caller getVariable [QGVAR(selectedWeaponOnrepair), ""]);
|
||||
|
@ -107,6 +107,14 @@ private _category = format ["ACE %1", LLSTRING(Repair)];
|
||||
{[QGVAR(engineerSetting_fullRepair), _this] call EFUNC(common,cbaSettings_settingChanged)}
|
||||
] call CBA_fnc_addSetting;
|
||||
|
||||
[
|
||||
QGVAR(timeCoefficientFullRepair), "SLIDER",
|
||||
[LSTRING(timeCoefficientFullRepair_name), LSTRING(timeCoefficientFullRepair_description)],
|
||||
_category,
|
||||
[0,3,1.5,2],
|
||||
true
|
||||
] call CBA_fnc_addSetting;
|
||||
|
||||
[
|
||||
QGVAR(addSpareParts), "CHECKBOX",
|
||||
[LSTRING(addSpareParts_name), LSTRING(addSpareParts_description)],
|
||||
@ -153,6 +161,21 @@ private _category = format ["ACE %1", LLSTRING(Repair)];
|
||||
{[QGVAR(autoShutOffEngineWhenStartingRepair), _this] call EFUNC(common,cbaSettings_settingChanged)}
|
||||
] call CBA_fnc_addSetting;
|
||||
|
||||
[
|
||||
QGVAR(miscRepairTime), "SLIDER",
|
||||
[LSTRING(miscRepairTime_name), LSTRING(miscRepairTime_description)],
|
||||
_category,
|
||||
[0,60,15,-1], // [min, max, default value, trailing decimals (-1 for whole numbers only)]
|
||||
true
|
||||
] call CBA_fnc_addSetting;
|
||||
|
||||
[
|
||||
QGVAR(wheelChangeTime), "SLIDER",
|
||||
[LSTRING(wheelChangeTime_name), LSTRING(wheelChangeTime_description)],
|
||||
_category,
|
||||
[0,60,10,-1], // [min, max, default value, trailing decimals (-1 for whole numbers only)]
|
||||
true
|
||||
] call CBA_fnc_addSetting;
|
||||
|
||||
[
|
||||
QGVAR(patchWheelTime),
|
||||
|
@ -20,6 +20,10 @@
|
||||
|
||||
#define DAMAGE_COLOR_SCALE ["#FFFFFF", "#FFFF7E", "#FFEC4D", "#FFD52C", "#FCB121", "#FF9916", "#FF7D16", "#FF4400", "#FF0000"]
|
||||
|
||||
#define IN_REPAIR_FACILITY_CACHE_EXPIRY 1
|
||||
|
||||
#define NEAR_REPAIR_VEHICLE_CACHE_EXPIRY 1
|
||||
|
||||
#define ANY_TOOLKIT_FAKECLASS QGVAR(anyToolKit)
|
||||
|
||||
#define PATCH_WHEEL_STEP_TIME 0.05
|
||||
|
@ -266,6 +266,12 @@
|
||||
<Chinese>維修載具中...</Chinese>
|
||||
<Turkish>Tamir Ediliyor...</Turkish>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_timeCoefficientFullRepair_name">
|
||||
<English>Full Repair Time Coefficient</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_timeCoefficientFullRepair_description">
|
||||
<English>Modifies how long it takes to perform a Full Repair.\nThe repair time is based on based on the amount of repairs needed for each part, including those normally inaccessible.</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_LocationsBoostTraining_Description">
|
||||
<English>Boost engineer training when in repair vehicles or facilities. Untrained becomes engineer, engineer becomes advanced engineer.</English>
|
||||
<French>Améliore les compétences en ingénierie des unités en fonction du lieu où elles se trouvent ; notamment dans les véhicules de réparation ou les ateliers.\nUn soldat non formé devient ingénieur, un ingénieur devient ingénieur avancé.</French>
|
||||
@ -1860,7 +1866,7 @@
|
||||
<Chinese>選擇的備件數量</Chinese>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_WheelRepairRequiredItems_DisplayName">
|
||||
<English>Wheel Repair Requirements</English>
|
||||
<English>Wheel Change Requirements</English>
|
||||
<German>Bedingungen für die Reifenreperatur</German>
|
||||
<Polish>Wym. naprawy kół</Polish>
|
||||
<Spanish>Requisitos de reparación de ruedas</Spanish>
|
||||
@ -2062,6 +2068,18 @@
|
||||
<Spanish>Apagar el motor automáticamente al efectuar una reparación</Spanish>
|
||||
<Korean>수리 시 엔진을 자동으로 끕니다.</Korean>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_miscRepairTime_name">
|
||||
<English>Part Repair Time</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_miscRepairTime_description">
|
||||
<English>Time in seconds to complete a repair.</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_wheelChangeTime_name">
|
||||
<English>Wheel Change Time</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_wheelChangeTime_description">
|
||||
<English>Time in seconds to remove or change a wheel.</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_PatchWheel">
|
||||
<English>Patch Wheel</English>
|
||||
<German>Radflicken</German>
|
||||
@ -2071,16 +2089,16 @@
|
||||
<German>Radflicken...</German>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_patchWheelTime_DisplayName">
|
||||
<English>Patch wheel time</English>
|
||||
<English>Wheel Patch Time</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_patchWheelTime_Description">
|
||||
<English>Time it takes to patch a wheel by 5%.</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_patchWheelMaximumRepair_DisplayName">
|
||||
<English>Patch wheel maximum repair</English>
|
||||
<English>Patch Wheel Threshold</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_patchWheelMaximumRepair_Description">
|
||||
<English>Maximum level a wheel can be patched.</English>
|
||||
<English>Maximum level to which a wheel can be patched.</English>
|
||||
</Key>
|
||||
<Key ID="STR_ACE_Repair_patchWheelLocation_DisplayName">
|
||||
<English>Wheel Patch Location</English>
|
||||
|
Loading…
Reference in New Issue
Block a user