Added methods to retrieve impact surface type

This commit is contained in:
lambdatiger 2024-01-09 17:25:09 -06:00
parent ed116f1b2b
commit 026e12b2f9
7 changed files with 95 additions and 38 deletions

View File

@ -8,12 +8,7 @@
class CfgAmmo {
class B_65x39_Caseless;
#include "cfgAmmoBaseEH.hpp"
#include "cfgAmmoSpall.hpp"
#include "cfgAmmoFragAddition.hpp"
#include "cfgAmmoFragSpawner.hpp"
class GVAR(base): B_65x39_Caseless {
class GVAR(base): B_65x39_Caseless {
ACE_damageType = "grenade"; // compatibility with medical_damage, shrapnel should produce grenade wounds
timeToLive = 4;
typicalSpeed = 800;
@ -89,4 +84,9 @@ class CfgAmmo {
airFriction = QUOTE(BASE_DRAG_HD*0.5);
caliber = 2.8;
};
#include "cfgAmmoBaseEH.hpp"
#include "cfgAmmoSpall.hpp"
#include "cfgAmmoFragParameters.hpp"
#include "cfgAmmoFragSpawner.hpp"
};

View File

@ -29,6 +29,7 @@ PREP(doFragRandom);
PREP(shouldSpall);
PREP(doSpall);
PREP(doSpallMomentum);
PREP(getMaterialInfo);
//PREP(spallHP); Look at me !*!
// Explosive Reflection

View File

@ -7,8 +7,8 @@ PREP_RECOMPILE_START;
PREP_RECOMPILE_END;
GVAR(materialSpallCache) = createHashMap;
GVAR(spallRoundCache) = createHashMapFromArray [["", "metal"]];
GVAR(materialSpallCache) = createHashMapFromArray [["", "metal"]];
GVAR(spallRoundCache) = createHashMap;
GVAR(lastSpallTime) = -2;
GVAR(shouldFragCache) = createHashMap;

View File

@ -15,24 +15,28 @@
*
* Public: No
*/
TRACE_1("",_this);
params [
"_projectile",
["_hitObj", objNull],
"",
// "",
["_lPosASL", [0, 0, 0]],
["_lVel", [0, 0, 0]],
"",
"",
"",
["_surfaceType", ""]
// "",
// "",
// "",
["_surfaceType", ""],
["_ammo", "", [""]],
["_shotParents", [objNull, objNull], [[]]],
["_vUp", [0,0,1]]
];
if (CBA_missionTime - GVAR(lastSpallTime) < ACE_FRAG_SPALL_HOLDOFF) exitWith {
TRACE_2("timeExit",CBA_missionTime,GVAR(lastSpallTime));
};
if (!(isNull _hitObj) && {_hitObj isKindOf "man"}) exitWith {
TRACE_1("hitPerson",_hitObj);
if (isNull _hitObj || {_hitObj isKindOf "man"}) exitWith {
TRACE_1("invalidHit",_hitObj);
};
if (_lPosASL isEqualTo [0,0,0]) exitWith {
@ -48,7 +52,6 @@ private _lVelUnit = vectorNormalized _lVel;
// Find spall speed / fragment
private _ammo = typeOf _projectile;
private _dV = vectorMagnitude _lVel - vectorMagnitude _vel;
private _caliber = getNumber (configFile >> "cfgAmmo" >> _ammo >> "caliber"); // !*! optimize this later?
// scaled momentum change made on caliber-mass assumption ~sqrt(2)/20 * caliber ~= mass
@ -60,6 +63,9 @@ if (_deltaMomentum < 2) exitWith {
TRACE_1("lowImpulse",_ammo);
};
private _material = [_surfaceType] call FUNC(getMaterialInfo);
TRACE_1("materialCacheRetrieved",_material);
//** start calculating where the spalling should come !*! could be better **//
private _unitStep = _lVelUnit vectorMultiply 0.05;
private _spallPos = +_lPosASL;
@ -79,9 +85,11 @@ for "_i" from 1 to 20 do
};
#ifdef DEBUG_MODE_FULL
[_spallPos, "green"] call FUNC(dev_sphereDraw);
[_lPosASL vectorAdd _lVelUnit, "orange"] call FUNC(dev_sphereDraw);
[_lPosASL, "orange"] call FUNC(dev_sphereDraw);
if GVAR(dbgSphere) then {
[_spallPos, "green"] call FUNC(dev_sphereDraw);
[_lPosASL vectorAdd _lVelUnit, "orange"] call FUNC(dev_sphereDraw);
[_lPosASL, "orange"] call FUNC(dev_sphereDraw);
};
#endif
//***** Passed all other exit withs, performance o'clock */
@ -89,7 +97,6 @@ GVAR(lastSpallTime) = CBA_missionTime;
//***** Select spalled fragment spawner **//
private _material = [_surfaceType] call FUNC(getMaterialInfo);
private _fragSpawnType = switch (true) do
{
@ -100,14 +107,11 @@ private _fragSpawnType = switch (true) do
default { QGVAR(spall_huge) };
};
// Shot parent
private _shotParent = getShotParents _projectile;
//***** Spawn spalled fragments
private _spallSpawner = createVehicleLocal [_fragSpawnType, ASLToATL _spallPos, [], 0, "CAN_COLLIDE"];
_spallSpawner setVectorDirandUp [vectorDir _projectile, vectorUp _projectile];
_spallSpawner setVectorDirandUp [_lVelUnit, _vUp];
_spallSpawner setVelocity (_lVelUnit vectorMultiply (_dV/2));
_spallSpawner setShotParents _shotParent;
_spallSpawner setShotParents _shotParents;
#ifdef DEBUG_MODE_FULL
systemChat ("bSpd: " + str speed _spallSpawner + ", frag: " + _fragSpawnType + ", dm: " + str _deltaMomentum);

View File

@ -25,11 +25,40 @@ params ["_surfType"];
private _material = GVAR(materialSpallCache) get _surfType;
if !(isNil "_material") exitWith {_material};
TRACE_2("materialCache",_surfType,_material);
if !(isNil "_material") exitWith {
_material
};
private _str = GVAR(materialSpallCache) getOrDefault [str _surfaceType, "["];
_str =_str + str [_dV, _caliber, abs vectorMagnitude (_lPosASL vectorDiff _spallPos)] + ";";
if (isClass (configFile >> "CfgSurfaces" >> _surfType)) then {
_material = getText (configFile >> "CfgSurfaces" >> _surfType >> "soundEnviron");
} else { // Messy way when a surface isn't added to cfgSurfaces
private _surfFileText = loadFile _surfType;
_surfFileText = (tolower _surfFileText) splitString " ;="+ endl;
private _idx = _surfFileText find "soundenviron";
_material = _surfFileText#(_idx+1);
if (_material isEqualTo "empty") then {
_idx = _surfFileText find "soundhit";
_material = _surfFileText#(_idx+1);
};
};
TRACE_1("soundFound",_material);
GVAR(materialSpallCache) set [_surfaceType, _material];
_material = switch (true) do {
case ("dirt" in _material);
case ("grass" in _material): { "ground" };
case ("gravel" in _material);
case ("rock" in _material): { "rock" };
case ("wood" in _material): { "wood" };
case ("lino" in _material);
case ("building" isEqualTo _material);
case ("concrete" in _material): { "concrete" };
case ("metal" in _material): { "metal" };
default { "ground" };
};
GVAR(materialSpallCache) set [_surfType, _material];
TRACE_2("materialCacheSet",_surfType,_material);
_material

View File

@ -15,7 +15,7 @@
* Public: No
*/
params [
["_projectile", objNull, [objNull]]
["_projectile", objNull, [objNull]]
];
private _ammo = typeOf _projectile;
@ -29,12 +29,21 @@ _shouldFrag params ["_doFrag"];
if (_doFrag) then {
// wait for frag damage to kill units before spawning fragments
_projectile addEventHandler [
"Explode",
{
"Explode",
{
params ["_proj"];
private _shotParents = getShotParents _proj;
private _ammo = typeOf _proj;
if (isServer) then {
[FUNC(doFrag), [_this]] call CBA_fnc_execNextFrame;
[
FUNC(doFrag),
_this + [_ammo, _shotParents]
] call CBA_fnc_execNextFrame;
} else {
[QGVAR(frag_eh), [_this]] call CBA_fnc_serverEvent;
[
QGVAR(frag_eh),
[_this + [_ammo, _shotParents]]
] call CBA_fnc_serverEvent;
};
}
];
@ -45,13 +54,26 @@ private _shouldSpall = _ammo call FUNC(shouldSpall);
if (GVAR(spallEnabled) && {_shouldSpall}) then
{
_projectile addEventHandler [
_projectile addEventHandler [
"HitPart",
{
params ["_proj", "_hitObj", "",
"_posASL", "_vel", "", "",
"", "surfType"
];
private _shotPrnt = getShotParents _proj;
private _ammo = typeOf _proj;
private _vUp = vectorUp _proj;
if (isServer) then {
[LINKFUNC(doSpallMomentum), _this] call CBA_fnc_execNextFrame;
[
LINKFUNC(doSpallMomentum),
[_proj, _hitObj, _posASL, _vel, surfType, _shotPrnt, _ammo, _vUp]
] call CBA_fnc_execNextFrame;
} else {
[QGVAR(spall_eh), [_this]] call CBA_fnc_serverEvent;
[
QGVAR(spall_eh),
[_proj, _hitObj, _posASL, _vel, surfType, _shotPrnt, _ammo, _vUp]
] call CBA_fnc_serverEvent;
};
}
];

View File

@ -17,7 +17,8 @@
#include "\z\ace\addons\main\script_macros.hpp"
#define ACE_FRAG_HOLDOFF 1
#define ACE_FRAG_HOLDOFF 0.2
#define ACE_FRAG_HOLDOFF_VEHICLE 1
#define ACE_FRAG_SPALL_HOLDOFF 0.2
#define ACE_FRAG_COUNT_MIN 5
#define ACE_FRAG_COUNT_MAX 50