mirror of
https://github.com/acemod/ACE3.git
synced 2024-08-30 18:23:18 +00:00
Medical - Increase severity of falling damage and Improve non-selectionSpecific wounds (#7214)
* Medical - Increase severity of falling damage * Improve non-selectionSpecific wounds * Use macros for hitpoint indexes
This commit is contained in:
parent
f4dbe5229e
commit
a71879ccea
@ -47,7 +47,6 @@ class ACE_Medical_Injuries {
|
|||||||
};
|
};
|
||||||
// Also called tears, these are separating wounds that produce ragged edges. They are produced by a tremendous force against the body, either from an internal source as in childbirth, or from an external source like a punch.
|
// Also called tears, these are separating wounds that produce ragged edges. They are produced by a tremendous force against the body, either from an internal source as in childbirth, or from an external source like a punch.
|
||||||
class Laceration {
|
class Laceration {
|
||||||
selections[] = {"All"};
|
|
||||||
causes[] = {"vehiclecrash", "collision", "punch"};
|
causes[] = {"vehiclecrash", "collision", "punch"};
|
||||||
bleeding = 0.05;
|
bleeding = 0.05;
|
||||||
pain = 0.2;
|
pain = 0.2;
|
||||||
@ -94,11 +93,11 @@ class ACE_Medical_Injuries {
|
|||||||
selectionSpecific = 0;
|
selectionSpecific = 0;
|
||||||
};
|
};
|
||||||
class vehiclecrash {
|
class vehiclecrash {
|
||||||
thresholds[] = {{0.5, 5}, {0.3, 2}, {0.05, 1}};
|
thresholds[] = {{1.5, 3}, {1, 2}, {0.05, 1}}; // prevent subdividing wounds past FRACTURE_DAMAGE_THRESHOLD to ensure limp/fractue is triggered
|
||||||
selectionSpecific = 0;
|
selectionSpecific = 0;
|
||||||
};
|
};
|
||||||
class collision {
|
class collision {
|
||||||
thresholds[] = {{0.5, 5}, {0.3, 2}, {0.05, 1}};
|
thresholds[] = {{1.5, 3}, {1, 2}, {0.05, 1}}; // prevent subdividing wounds past FRACTURE_DAMAGE_THRESHOLD to ensure limp/fractue is triggered
|
||||||
selectionSpecific = 0;
|
selectionSpecific = 0;
|
||||||
};
|
};
|
||||||
class backblast {
|
class backblast {
|
||||||
@ -114,8 +113,8 @@ class ACE_Medical_Injuries {
|
|||||||
selectionSpecific = 1;
|
selectionSpecific = 1;
|
||||||
};
|
};
|
||||||
class falling {
|
class falling {
|
||||||
thresholds[] = {{0.6, 4}, {0.35, 2}, {0.1, 1}};
|
thresholds[] = {{1.5, 3}, {1, 2}, {0.05, 1}}; // prevent subdividing wounds past FRACTURE_DAMAGE_THRESHOLD to ensure limp/fractue is triggered
|
||||||
selectionSpecific = 1;
|
selectionSpecific = 0;
|
||||||
};
|
};
|
||||||
class ropeburn {
|
class ropeburn {
|
||||||
thresholds[] = {{0.1, 1}};
|
thresholds[] = {{0.1, 1}};
|
||||||
|
@ -26,10 +26,10 @@ addMissionEventHandler ["Loaded",{
|
|||||||
// };
|
// };
|
||||||
|
|
||||||
[QEGVAR(medical,woundReceived), {
|
[QEGVAR(medical,woundReceived), {
|
||||||
params ["_unit", "_woundedHitPoint", "_receivedDamage", "", "_ammo"];
|
params ["_unit", "_woundedHitPoint", "_receivedDamage", "", "_ammo", "_damageSelectionArray"];
|
||||||
|
|
||||||
private _typeOfDamage = _ammo call FUNC(getTypeOfDamage);
|
private _typeOfDamage = _ammo call FUNC(getTypeOfDamage);
|
||||||
[_unit, _woundedHitPoint, _receivedDamage, _typeOfDamage] call FUNC(woundsHandlerActive);
|
[_unit, _woundedHitPoint, _receivedDamage, _typeOfDamage, _damageSelectionArray] call FUNC(woundsHandlerActive);
|
||||||
}] call CBA_fnc_addEventHandler;
|
}] call CBA_fnc_addEventHandler;
|
||||||
|
|
||||||
ADDON = true;
|
ADDON = true;
|
||||||
|
@ -76,6 +76,7 @@ private _selectionSpecificDefault = getNumber (_damageTypesConfig >> "selectionS
|
|||||||
|
|
||||||
GVAR(allDamageTypesData) setVariable [_className, [_thresholds, _selectionSpecific > 0, _woundTypes]];
|
GVAR(allDamageTypesData) setVariable [_className, [_thresholds, _selectionSpecific > 0, _woundTypes]];
|
||||||
|
|
||||||
|
/*
|
||||||
// extension loading
|
// extension loading
|
||||||
private _minDamageThresholds = (_thresholds apply {str (_x select 0)}) joinString ":";
|
private _minDamageThresholds = (_thresholds apply {str (_x select 0)}) joinString ":";
|
||||||
private _amountThresholds = (_thresholds apply {str (_x select 1)}) joinString ":";
|
private _amountThresholds = (_thresholds apply {str (_x select 1)}) joinString ":";
|
||||||
@ -93,8 +94,10 @@ private _selectionSpecificDefault = getNumber (_damageTypesConfig >> "selectionS
|
|||||||
|
|
||||||
// private _extensionRes = "ace_medical" callExtension _extensionArgs;
|
// private _extensionRes = "ace_medical" callExtension _extensionArgs;
|
||||||
// TRACE_1("",_extensionRes);
|
// TRACE_1("",_extensionRes);
|
||||||
|
*/
|
||||||
} forEach configProperties [_damageTypesConfig, "isClass _x"];
|
} forEach configProperties [_damageTypesConfig, "isClass _x"];
|
||||||
|
|
||||||
|
/*
|
||||||
// extension loading
|
// extension loading
|
||||||
{
|
{
|
||||||
_x params ["_classID", "_selections", "_bleedingRate", "_pain", "_damageExtrema", "_causes", "_displayName"];
|
_x params ["_classID", "_selections", "_bleedingRate", "_pain", "_damageExtrema", "_causes", "_displayName"];
|
||||||
@ -128,3 +131,4 @@ private _selectionSpecificDefault = getNumber (_damageTypesConfig >> "selectionS
|
|||||||
} forEach GVAR(woundsData);
|
} forEach GVAR(woundsData);
|
||||||
|
|
||||||
// "ace_medical" callExtension "ConfigComplete";
|
// "ace_medical" callExtension "ConfigComplete";
|
||||||
|
*/
|
||||||
|
@ -8,18 +8,19 @@
|
|||||||
* 1: Name Of Body Part <STRING>
|
* 1: Name Of Body Part <STRING>
|
||||||
* 2: Amount Of Damage <NUMBER>
|
* 2: Amount Of Damage <NUMBER>
|
||||||
* 3: Type of the damage done <STRING>
|
* 3: Type of the damage done <STRING>
|
||||||
|
* 4: Weighted array of damaged selections <ARRAY>
|
||||||
*
|
*
|
||||||
* Return Value:
|
* Return Value:
|
||||||
* None
|
* None
|
||||||
*
|
*
|
||||||
* Example:
|
* Example:
|
||||||
* [player, "Body", 0.5, "bullet"] call ace_medical_damage_fnc_woundsHandlerSQF
|
* [player, "Body", 0.5, "bullet", [1, 1]] call ace_medical_damage_fnc_woundsHandlerSQF
|
||||||
*
|
*
|
||||||
* Public: No
|
* Public: No
|
||||||
*/
|
*/
|
||||||
|
|
||||||
params ["_unit", "_bodyPart", "_damage", "_typeOfDamage"];
|
params ["_unit", "_bodyPart", "_damage", "_typeOfDamage", "_damageSelectionArray"];
|
||||||
TRACE_4("woundsHandlerSQF",_unit,_bodyPart,_damage,_typeOfDamage);
|
TRACE_5("woundsHandlerSQF",_unit,_bodyPart,_damage,_typeOfDamage,_damageSelectionArray);
|
||||||
|
|
||||||
// Convert the selectionName to a number and ensure it is a valid selection.
|
// Convert the selectionName to a number and ensure it is a valid selection.
|
||||||
private _bodyPartN = ALL_BODY_PARTS find toLower _bodyPart;
|
private _bodyPartN = ALL_BODY_PARTS find toLower _bodyPart;
|
||||||
@ -47,7 +48,7 @@ private _allPossibleInjuries = [];
|
|||||||
// Check if the damage is higher as the min damage for the specific injury
|
// Check if the damage is higher as the min damage for the specific injury
|
||||||
if (_damage >= _minDamage && {_damage <= _maxDamage || _maxDamage < 0}) then {
|
if (_damage >= _minDamage && {_damage <= _maxDamage || _maxDamage < 0}) then {
|
||||||
// Check if the injury can be applied to the given selection name
|
// Check if the injury can be applied to the given selection name
|
||||||
if ("All" in _selections || {_bodyPart in _selections}) then { // @todo, this is case sensitive!
|
// if ("All" in _selections || {_bodyPart in _selections}) then { // @todo, this is case sensitive! [we have no injuries that use this, disabled for now]
|
||||||
|
|
||||||
// Find the wound which has the highest minimal damage, so we can use this later on for adding the correct injuries
|
// Find the wound which has the highest minimal damage, so we can use this later on for adding the correct injuries
|
||||||
if (_minDamage > _highestPossibleDamage) then {
|
if (_minDamage > _highestPossibleDamage) then {
|
||||||
@ -57,7 +58,7 @@ private _allPossibleInjuries = [];
|
|||||||
|
|
||||||
// Store the valid possible injury for the damage type, damage amount and selection
|
// Store the valid possible injury for the damage type, damage amount and selection
|
||||||
_allPossibleInjuries pushBack _x;
|
_allPossibleInjuries pushBack _x;
|
||||||
};
|
// };
|
||||||
};
|
};
|
||||||
} forEach _woundTypes;
|
} forEach _woundTypes;
|
||||||
|
|
||||||
@ -87,7 +88,7 @@ private _bodyPartVisParams = [_unit, false, false, false, false]; // params arra
|
|||||||
|
|
||||||
_oldInjury params ["_woundClassIDToAdd", "", "_injuryBleedingRate", "_injuryPain", "", "", "", "_causeLimping", "_causeFracture"];
|
_oldInjury params ["_woundClassIDToAdd", "", "_injuryBleedingRate", "_injuryPain", "", "", "", "_causeLimping", "_causeFracture"];
|
||||||
|
|
||||||
private _bodyPartNToAdd = [floor random 6, _bodyPartN] select _isSelectionSpecific; // 6 == count ALL_BODY_PARTS
|
private _bodyPartNToAdd = if (_isSelectionSpecific) then {_bodyPartN} else {selectRandomWeighted _damageSelectionArray};
|
||||||
|
|
||||||
_bodyPartDamage set [_bodyPartNToAdd, (_bodyPartDamage select _bodyPartNToAdd) + _woundDamage];
|
_bodyPartDamage set [_bodyPartNToAdd, (_bodyPartDamage select _bodyPartNToAdd) + _woundDamage];
|
||||||
_bodyPartVisParams set [[1,2,3,3,4,4] select _bodyPartNToAdd, true]; // Mark the body part index needs updating
|
_bodyPartVisParams set [[1,2,3,3,4,4] select _bodyPartNToAdd, true]; // Mark the body part index needs updating
|
||||||
|
@ -80,6 +80,12 @@ if (_hitPoint isEqualTo "ace_hdbracket") exitWith {
|
|||||||
];
|
];
|
||||||
TRACE_2("incoming",_allDamages,_damageStructural);
|
TRACE_2("incoming",_allDamages,_damageStructural);
|
||||||
|
|
||||||
|
// represents all incoming damage for selecting a non-selectionSpecific wound location, (used for selectRandomWeighted [value1,weight1,value2....])
|
||||||
|
private _damageSelectionArray = [
|
||||||
|
HITPOINT_INDEX_HEAD, _damageHead, HITPOINT_INDEX_BODY, _damageBody, HITPOINT_INDEX_LARM, _damageLeftArm,
|
||||||
|
HITPOINT_INDEX_RARM, _damageRightArm, HITPOINT_INDEX_LLEG, _damageLeftLeg, HITPOINT_INDEX_RLEG, _damageRightLeg
|
||||||
|
];
|
||||||
|
|
||||||
_allDamages sort false;
|
_allDamages sort false;
|
||||||
(_allDamages select 0) params ["_receivedDamage", "", "_woundedHitPoint"];
|
(_allDamages select 0) params ["_receivedDamage", "", "_woundedHitPoint"];
|
||||||
if (_damageHead >= HEAD_DAMAGE_THRESHOLD) then {
|
if (_damageHead >= HEAD_DAMAGE_THRESHOLD) then {
|
||||||
@ -92,6 +98,7 @@ if (_hitPoint isEqualTo "ace_hdbracket") exitWith {
|
|||||||
if (_receivedDamage == 0) then {
|
if (_receivedDamage == 0) then {
|
||||||
_receivedDamage = _damageStructural;
|
_receivedDamage = _damageStructural;
|
||||||
_woundedHitPoint = "Body";
|
_woundedHitPoint = "Body";
|
||||||
|
_damageSelectionArray = [1, 1]; // sum of weights would be 0
|
||||||
};
|
};
|
||||||
|
|
||||||
// Environmental damage sources all have empty ammo string
|
// Environmental damage sources all have empty ammo string
|
||||||
@ -100,7 +107,7 @@ if (_hitPoint isEqualTo "ace_hdbracket") exitWith {
|
|||||||
// Any collision with terrain/vehicle/object has a shooter
|
// Any collision with terrain/vehicle/object has a shooter
|
||||||
// Check this first because burning can happen at any velocity
|
// Check this first because burning can happen at any velocity
|
||||||
if !(isNull _shooter) then {
|
if !(isNull _shooter) then {
|
||||||
_ammo = "#collision";
|
_ammo = "#collision"; // non-selectionSpecific so only _damageSelectionArray matters
|
||||||
|
|
||||||
/*
|
/*
|
||||||
If shooter != unit then they hit unit, otherwise it could be:
|
If shooter != unit then they hit unit, otherwise it could be:
|
||||||
@ -110,10 +117,11 @@ if (_hitPoint isEqualTo "ace_hdbracket") exitWith {
|
|||||||
Assume fall damage for downward velocity because it's most common
|
Assume fall damage for downward velocity because it's most common
|
||||||
*/
|
*/
|
||||||
if (_shooter == _unit && {(velocity _unit select 2) < -2}) then {
|
if (_shooter == _unit && {(velocity _unit select 2) < -2}) then {
|
||||||
_woundedHitPoint = selectRandom ["RightLeg", "LeftLeg"];
|
_ammo = "#falling"; // non-selectionSpecific so only _damageSelectionArray matters
|
||||||
|
_damageSelectionArray = [4, 1, 5, 1]; // selectRandom ["RightLeg", "LeftLeg"];
|
||||||
TRACE_5("Fall",_unit,_shooter,_instigator,_damage,_receivedDamage);
|
TRACE_5("Fall",_unit,_shooter,_instigator,_damage,_receivedDamage);
|
||||||
} else {
|
} else {
|
||||||
_woundedHitPoint = selectRandom ["RightArm", "LeftArm", "RightLeg", "LeftLeg"];
|
_damageSelectionArray = [2, 1, 3, 1, 4, 1, 5, 1]; // selectRandom ["RightArm", "LeftArm", "RightLeg", "LeftLeg"];
|
||||||
TRACE_5("Collision",_unit,_shooter,_instigator,_damage,_receivedDamage);
|
TRACE_5("Collision",_unit,_shooter,_instigator,_damage,_receivedDamage);
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -122,12 +130,16 @@ if (_hitPoint isEqualTo "ace_hdbracket") exitWith {
|
|||||||
// Higher momentum results in higher chance for head to be hit for more lethality
|
// Higher momentum results in higher chance for head to be hit for more lethality
|
||||||
if (_receivedDamage > 0.35) then {
|
if (_receivedDamage > 0.35) then {
|
||||||
private _headHitWeight = (_receivedDamage / 2) min 1;
|
private _headHitWeight = (_receivedDamage / 2) min 1;
|
||||||
_woundedHitPoint = selectRandomWeighted ["Body", (1 - _headHitWeight), "Head", _headHitWeight];
|
if (_recievedDamage < 0.6) then {
|
||||||
|
_damageSelectionArray append [0, (1 - _headHitWeight), 1, _headHitWeight];
|
||||||
|
} else {
|
||||||
|
_damageSelectionArray = [0, (1 - _headHitWeight), 1, _headHitWeight];
|
||||||
|
}
|
||||||
};
|
};
|
||||||
} else {
|
} else {
|
||||||
// Anything else is almost guaranteed to be fire damage
|
// Anything else is almost guaranteed to be fire damage
|
||||||
_woundedHitPoint = selectRandom ["LeftLeg", "RightLeg", "Body"];
|
_damageSelectionArray = [1, 1, 4, 1, 5, 1]; // selectRandom ["Body", "LeftLeg", "RightLeg"];
|
||||||
_ammo = "#unknown";
|
_ammo = "#unknown"; // non-selectionSpecific so only _damageSelectionArray matters
|
||||||
|
|
||||||
// Fire damage can occur as lots of minor damage events
|
// Fire damage can occur as lots of minor damage events
|
||||||
// Combine these until significant enough to wound
|
// Combine these until significant enough to wound
|
||||||
@ -145,8 +157,8 @@ if (_hitPoint isEqualTo "ace_hdbracket") exitWith {
|
|||||||
|
|
||||||
// No wounds for minor damage
|
// No wounds for minor damage
|
||||||
if (_receivedDamage > 1E-3) then {
|
if (_receivedDamage > 1E-3) then {
|
||||||
[QEGVAR(medical,woundReceived), [_unit, _woundedHitPoint, _receivedDamage, _shooter, _ammo]] call CBA_fnc_localEvent;
|
TRACE_3("received",_receivedDamage,_woundedHitPoint,_damageSelectionArray);
|
||||||
TRACE_2("received",_receivedDamage,_woundedHitPoint);
|
[QEGVAR(medical,woundReceived), [_unit, _woundedHitPoint, _receivedDamage, _shooter, _ammo, _damageSelectionArray]] call CBA_fnc_localEvent;
|
||||||
};
|
};
|
||||||
|
|
||||||
// Clear stored damages otherwise they will influence future damage events
|
// Clear stored damages otherwise they will influence future damage events
|
||||||
@ -169,7 +181,7 @@ if (
|
|||||||
{getOxygenRemaining _unit <= 0.5} &&
|
{getOxygenRemaining _unit <= 0.5} &&
|
||||||
{_damage isEqualTo (_oldDamage + 0.005)}
|
{_damage isEqualTo (_oldDamage + 0.005)}
|
||||||
) exitWith {
|
) exitWith {
|
||||||
[QEGVAR(medical,woundReceived), [_unit, "Body", _newDamage, _unit, "#drowning"]] call CBA_fnc_localEvent;
|
[QEGVAR(medical,woundReceived), [_unit, "Body", _newDamage, _unit, "#drowning", [HITPOINT_INDEX_BODY, 1]]] call CBA_fnc_localEvent;
|
||||||
TRACE_5("Drowning",_unit,_shooter,_instigator,_damage,_newDamage);
|
TRACE_5("Drowning",_unit,_shooter,_instigator,_damage,_newDamage);
|
||||||
|
|
||||||
0
|
0
|
||||||
@ -185,7 +197,11 @@ if (
|
|||||||
{vectorMagnitude (velocity _vehicle) > 5}
|
{vectorMagnitude (velocity _vehicle) > 5}
|
||||||
// todo: no way to detect if stationary and another vehicle hits you
|
// todo: no way to detect if stationary and another vehicle hits you
|
||||||
) exitWith {
|
) exitWith {
|
||||||
[QEGVAR(medical,woundReceived), [_unit, "Body", _newDamage, _unit, "#vehiclecrash"]] call CBA_fnc_localEvent;
|
private _damageSelectionArray = [
|
||||||
|
HITPOINT_INDEX_HEAD, 1, HITPOINT_INDEX_BODY, 1, HITPOINT_INDEX_LARM, 1,
|
||||||
|
HITPOINT_INDEX_RARM, 1, HITPOINT_INDEX_LLEG, 1, HITPOINT_INDEX_RLEG, 1
|
||||||
|
];
|
||||||
|
[QEGVAR(medical,woundReceived), [_unit, "Body", _newDamage, _unit, "#vehiclecrash", _damageSelectionArray]] call CBA_fnc_localEvent;
|
||||||
TRACE_5("Crash",_unit,_shooter,_instigator,_damage,_newDamage);
|
TRACE_5("Crash",_unit,_shooter,_instigator,_damage,_newDamage);
|
||||||
|
|
||||||
0
|
0
|
||||||
|
@ -6,6 +6,13 @@
|
|||||||
#define ALL_SELECTIONS ["head", "body", "hand_l", "hand_r", "leg_l", "leg_r"]
|
#define ALL_SELECTIONS ["head", "body", "hand_l", "hand_r", "leg_l", "leg_r"]
|
||||||
#define ALL_HITPOINTS ["HitHead", "HitBody", "HitLeftArm", "HitRightArm", "HitLeftLeg", "HitRightLeg"]
|
#define ALL_HITPOINTS ["HitHead", "HitBody", "HitLeftArm", "HitRightArm", "HitLeftLeg", "HitRightLeg"]
|
||||||
|
|
||||||
|
#define HITPOINT_INDEX_HEAD 0
|
||||||
|
#define HITPOINT_INDEX_BODY 1
|
||||||
|
#define HITPOINT_INDEX_LARM 2
|
||||||
|
#define HITPOINT_INDEX_RARM 3
|
||||||
|
#define HITPOINT_INDEX_LLEG 4
|
||||||
|
#define HITPOINT_INDEX_RLEG 5
|
||||||
|
|
||||||
// Damage threshold above which fatal organ damage can occur
|
// Damage threshold above which fatal organ damage can occur
|
||||||
#define HEAD_DAMAGE_THRESHOLD 1
|
#define HEAD_DAMAGE_THRESHOLD 1
|
||||||
#define ORGAN_DAMAGE_THRESHOLD 0.6
|
#define ORGAN_DAMAGE_THRESHOLD 0.6
|
||||||
|
Loading…
Reference in New Issue
Block a user