flashgrenade.c 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293
  1. class FlashGrenade extends Grenade_Base
  2. {
  3. const float FX_RANGE_MAX_MULT = 1.0;
  4. override void OnExplosionEffects(Object source, Object directHit, int componentIndex, string surface, vector pos, vector surfNormal, float energyFactor, float explosionFactor, bool isWater, string ammoType)
  5. {
  6. super.OnExplosionEffects(source, directHit, componentIndex, surface, pos, surfNormal, energyFactor, explosionFactor, isWater, ammoType);
  7. PlayerBase player = PlayerBase.Cast(GetGame().GetPlayer());
  8. if (player)
  9. {
  10. vector headPos = player.GetDamageZonePos("Head"); // animated position in the middle of the zone
  11. float ammoRangeKill = GetGame().ConfigGetFloat(string.Format("CfgAmmo %1 indirectHitRange", ammoType));
  12. float ammoRangeMaxMult = 4.0;
  13. string indirectHitRangeMultiplier = string.Format("CfgAmmo %1 indirectHitRangeMultiplier", ammoType);
  14. if (GetGame().ConfigIsExisting(indirectHitRangeMultiplier))
  15. {
  16. //! values less than 1.0 make no sense
  17. ammoRangeMaxMult = Math.Clamp(GetGame().ConfigGetFloat(indirectHitRangeMultiplier), 1.0, float.MAX);
  18. }
  19. float ammoRangeMax = ammoRangeKill * ammoRangeMaxMult;
  20. ammoRangeMax = Math.Clamp(ammoRangeMax * FX_RANGE_MAX_MULT, ammoRangeKill, ammoRangeMax);
  21. float dist = vector.Distance(headPos, pos);
  22. float distSq = vector.DistanceSq(headPos, pos);
  23. float radiusMaxSq = Math.SqrFloat(ammoRangeMax);
  24. if (distSq <= radiusMaxSq)
  25. {
  26. // ignore collisions with parent if fireplace
  27. InventoryItem invItem = InventoryItem.Cast(source);
  28. EntityAI parent = invItem.GetHierarchyParent();
  29. array<Object> excluded = new array<Object>;
  30. if (!parent || !parent.IsFireplace())
  31. parent = null;
  32. else if (parent)
  33. excluded.Insert(parent);
  34. array<ref RaycastRVResult> results = new array<ref RaycastRVResult>;
  35. excluded.Insert(this); //Ignore self for visibility check
  36. //There shouldn't be cases justifying we go further than first entry (if in fireplace, self does not impact)
  37. RaycastRVParams rayParams = new RaycastRVParams(pos, headPos, excluded[0]);
  38. rayParams.flags = CollisionFlags.ALLOBJECTS;
  39. DayZPhysics.RaycastRVProxy(rayParams, results, excluded);
  40. //! removes possible obstacles made by items around the grenade(or on the same position)
  41. array<Object> hitObjects = new array<Object>;
  42. for (int i = 0; i < results.Count(); i++)
  43. {
  44. if (results[i].obj && !results[i].obj.IsInherited(ItemBase))
  45. {
  46. hitObjects.Insert(results[i].obj);
  47. }
  48. }
  49. //If player is not first index, object is between player and grenade
  50. if (hitObjects.Count() && PlayerBase.Cast(hitObjects[0]))
  51. {
  52. float effectCoef;
  53. if (ammoRangeMax == ammoRangeKill)
  54. {
  55. effectCoef = 1.0; //edge case, landed right on the edge
  56. }
  57. effectCoef = 1 - ((dist - ammoRangeKill) / (ammoRangeMax - ammoRangeKill));
  58. effectCoef = Math.Clamp(effectCoef, 0.1, 100.0);
  59. player.OnPlayerReceiveFlashbangHitStart(MiscGameplayFunctions.IsPlayerOrientedTowardPos(player, pos, 60));
  60. player.GetFlashbangEffect().SetupFlashbangValues(effectCoef, effectCoef, effectCoef);
  61. }
  62. }
  63. }
  64. }
  65. void FlashGrenade()
  66. {
  67. SetAmmoType("FlashGrenade_Ammo");
  68. SetFuseDelay(2);
  69. SetGrenadeType(EGrenadeType.ILLUMINATING);
  70. SetParticleExplosion(ParticleList.GRENADE_M84);
  71. }
  72. protected override void CreateLight()
  73. {
  74. m_Light = ExplosiveLight.Cast(ScriptedLightBase.CreateLight(FlashGrenadeLight, GetPosition()));
  75. }
  76. void ~FlashGrenade() {}
  77. }