Dayz Explorer 1.28.160049
Loading...
Searching...
No Matches
dayzplayermeleefightlogic_lightheavy.c
Go to the documentation of this file.
1
6
8{
10 const float EVADE_COOLDOWN = 0.5;
11
12 //
13 const float CLOSE_TARGET_DISTANCE = 1.5;
14
16 const string DUMMY_LIGHT_AMMO = "Dummy_Light";
17 const string DUMMY_HEAVY_AMMO = "Dummy_Heavy";
18
20 protected ref DayZPlayerImplementMeleeCombat m_MeleeCombat;
23 protected Mission m_Mission;
24
25 protected bool m_IsInBlock;
26 protected bool m_IsEvading;
27
28 protected bool m_IsInComboRange;
30
35
37 {
38 m_DZPlayer = player;
39 m_Player = PlayerBase.Cast(player);
41 m_Mission = GetGame().GetMission();
42
43 m_IsInBlock = false;
44 m_IsEvading = false;
47
49 }
50
52
53 bool IsInBlock()
54 {
55 return m_IsInBlock;
56 }
57
58 void SetBlock(bool block)
59 {
60 m_IsInBlock = block;
61 }
62
63 bool IsEvading()
64 {
65 return m_IsEvading;
66 }
67
68 bool GetCurrentHitType()
69 {
70 return m_HitType;
71 }
72
73 bool CanFight()
74 {
75 if (m_Player.IsEmotePlaying())
76 return false;
77
78 if (m_Player.GetActionManager() && m_Player.GetActionManager().GetRunningAction())
79 return false;
80
81 return true;
82 }
83
89
91 {
92 if (pInputs.IsMeleeFastAttackModifier() && m_Player.CanConsumeStamina(EStaminaConsumers.MELEE_HEAVY))
93 {
94 return EMeleeHitType.HEAVY;
95 }
96
97 return EMeleeHitType.LIGHT;
98 }
99
101 {
103 {
104 return EMeleeHitType.NONE;
105 }
106
108 if (pEntity.HasBayonetAttached())
109 {
110 return EMeleeHitType.WPN_STAB;
111 }
112 else if (pEntity.HasButtstockAttached())
113 {
114 return EMeleeHitType.WPN_HIT_BUTTSTOCK;
115 }
116
117 return EMeleeHitType.WPN_HIT;
118 }
119
120 protected float GetAttackTypeByDistanceToTarget(EntityAI pTarget, EMeleeTargetType pTargetType = EMeleeTargetType.ALIGNABLE)
121 {
122 if (pTargetType == EMeleeTargetType.NONALIGNABLE)
123 {
124 return 1.0;
125 }
126
128 if (IsShortDistance(pTarget, Math.SqrFloat(CLOSE_TARGET_DISTANCE)))
129 {
130 return 1.0;
131 }
132
134 return 0.0;
135 }
136
137 bool HandleFightLogic(int pCurrentCommandID, HumanInputController pInputs, EntityAI pEntityInHands, HumanMovementState pMovementState, out bool pContinueAttack)
138 {
139 HumanInventoryWithFSM invFSM = HumanInventoryWithFSM.Cast(m_Player.GetHumanInventory());
140 if (invFSM && !invFSM.IsIdle())
141 return false;
142
143 HumanCommandMove hcm = m_Player.GetCommand_Move();
144 InventoryItem itemInHands = InventoryItem.Cast(pEntityInHands);
145 bool isFireWeapon = itemInHands && itemInHands.IsWeapon();
146
148 HandleHitEvent(pCurrentCommandID, pInputs, itemInHands, pMovementState, pContinueAttack);
149
151 if ((pInputs.IsAttackButtonDown() && !isFireWeapon) || (pInputs.IsMeleeWeaponAttack() && isFireWeapon) || (pContinueAttack && isFireWeapon))
152 {
153 //Debug.MeleeLog(m_Player, string.Format("HandleFightLogic[1] attackButtonDown=%1, meleeWeaponAttack=%2, pContinueAttack=%3, isFireWeapon=%4", pInputs.IsAttackButtonDown(), pInputs.IsMeleeWeaponAttack(), pContinueAttack, isFireWeapon));
154
157 return false;
158
160 if (itemInHands && !itemInHands.IsMeleeWeapon() && !isFireWeapon)
161 return false;
162
164 if (pCurrentCommandID == DayZPlayerConstants.COMMANDID_MOVE)
165 {
166 //Debug.MeleeLog(m_Player, "HandleFightLogic[1a]");
168 if (isFireWeapon)
169 {
170 return HandleInitialFirearmMelee(pCurrentCommandID, pInputs, itemInHands, pMovementState, pContinueAttack);
171 }
172 else
173 {
175 if (pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDERECT)
176 {
177 return HandleInitialMeleeErc(pCurrentCommandID, pInputs, itemInHands, pMovementState, pContinueAttack);
178 }
180 else if (pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDPRONE)
181 {
182 return HandleProneKick(pCurrentCommandID, pInputs, itemInHands, pMovementState, pContinueAttack);
183 }
185 else if (pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_ERECT && m_Player.IsSprintFull())
186 {
187 return HandleSprintAttack(pCurrentCommandID, pInputs, itemInHands, pMovementState, pContinueAttack);
188 }
189 }
190 }
192 else if (pCurrentCommandID == DayZPlayerConstants.COMMANDID_MELEE2)
193 {
194 m_IsInComboRange = m_Player.GetCommand_Melee2().IsInComboRange();
196 {
197 return HandleComboHit(pCurrentCommandID, pInputs, itemInHands, pMovementState, pContinueAttack);
198 }
199 }
200 }
202 else if (!isFireWeapon && pCurrentCommandID == DayZPlayerConstants.COMMANDID_MOVE)
203 {
205 if (pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDERECT)
206 {
207 int roll = pInputs.IsMeleeLREvade();
208 if (roll != 0)
209 {
212 {
213 return false;
214 }
215
216 float angle;
217 if (roll == 1)
218 {
219 angle = -90; // left
220 }
221 else
222 {
223 angle = 90; // right
224 }
225
226 // start melee evade
227 m_IsEvading = true;
229 hcm.StartMeleeEvadeA(angle);
231
232 //Inflict shock when sidestepping with broken legs
233 if (m_Player.GetBrokenLegs() == eBrokenLegs.BROKEN_LEGS)
234 {
235 m_Player.m_ShockHandler.SetShock(PlayerConstants.BROKEN_LEGS_LIGHT_MELEE_SHOCK);
236 m_Player.m_ShockHandler.CheckValue(true);
237 }
238 }
239 }
240
242 if (pInputs.IsWeaponRaised() && pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_CROUCH)
243 {
244 //Debug.MeleeLog(m_Player, "HandleFightLogic[2b]");
245 if (DayZPlayerUtils.PlayerCanChangeStance(m_Player, DayZPlayerConstants.STANCEIDX_RAISEDERECT))
246 {
247 //Debug.MeleeLog(m_Player, "HandleFightLogic[2c]");
248 hcm.ForceStance(DayZPlayerConstants.STANCEIDX_RAISEDERECT);
249
250 return false;
251 }
252 }
253
256 if (!isFireWeapon && (pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDERECT || pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDPRONE))
257 {
258 float angle2;
259
260 if (hcm.GetCurrentInputAngle(angle2) && (angle2 < -130.0 || angle2 > 130))
261 {
262 hcm.SetMeleeBlock(true);
263 SetBlock(true);
264 }
265 else
266 {
267 hcm.SetMeleeBlock(false);
268 SetBlock(false);
269 }
270 }
271 else
272 {
273 hcm.SetMeleeBlock(false);
274 SetBlock(false);
275 }
276 }
277
278 return false;
279 }
280
282 protected bool HandleHitEvent(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
283 {
285 if (pCurrentCommandID == DayZPlayerConstants.COMMANDID_MELEE2)
286 {
287 HumanCommandMelee2 hmc2a = m_Player.GetCommand_Melee2();
288 if (hmc2a)
289 {
291 if (hmc2a.WasHit())
292 {
293 //Debug.MeleeLog(m_Player, "HandleHitEvent[START]");
294 //Debug.MeleeLog(m_Player, string.Format("HandleHitEvent[1] target=%1, hitPos=%2, hitZoneIdx=%3, finisherType=%4", m_MeleeCombat.GetTargetEntity(), m_MeleeCombat.GetHitPos().ToString(), m_MeleeCombat.GetHitZoneIdx(), m_MeleeCombat.GetFinisherType()));
295 if (m_MeleeCombat.GetFinisherType() == -1)
296 {
297 //Debug.MeleeLog(m_Player, string.Format("HandleHitEvent[2] target=%1, hitPos=%2, hitZoneIdx=%3, finisherType=%4", m_MeleeCombat.GetTargetEntity(), m_MeleeCombat.GetHitPos().ToString(), m_MeleeCombat.GetHitZoneIdx(), m_MeleeCombat.GetFinisherType()));
299 m_MeleeCombat.Update(itemInHands, m_HitType, true);
300 }
301
303 EvaluateHit(itemInHands);
304
305 //Get gloves
306 ClothingBase gloves;
307 if (m_HitType == EMeleeHitType.KICK)
308 {
309 //We kick so "gloves" will be the shoes
310 gloves = ClothingBase.Cast(m_Player.GetItemOnSlot("FEET"));
311 }
312 else
313 {
314 gloves = ClothingBase.Cast(m_Player.GetItemOnSlot("GLOVES"));
315 }
316
317 //If we hit something, inflict damage
318 DamageHands(m_Player, gloves, itemInHands);
319
320 m_MeleeCombat.ResetTarget();
321
323
325
326 //Debug.MeleeLog(m_Player, "HandleHitEvent[END]");
327
328 return true;
329 }
330 }
331 }
332
333 return false;
334 }
335
337 protected bool HandleInitialFirearmMelee(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
338 {
340 Weapon_Base weapon = Weapon_Base.Cast(itemInHands);
341 if (weapon.IsWaitingForActionFinish())
342 return false;
343
344 HumanCommandMove hcm = m_Player.GetCommand_Move();
345
347 if (hcm.GetCurrentMovementSpeed() <= 2.05 && (pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDERECT || pContinueAttack) && !m_Player.IsFighting())
348 {
350 if ( m_HitType == EMeleeHitType.NONE )
351 {
352 pContinueAttack = false;
353 return false;
354 }
355
356 m_MeleeCombat.Update(itemInHands, m_HitType);
357
358 EntityAI target;
359 EMeleeTargetType targetType;
360 GetTargetData(target, targetType);
361 float attackByDistance = GetAttackTypeByDistanceToTarget(target, targetType);
362
363 m_Player.StartCommand_Melee2(target, m_HitType == EMeleeHitType.WPN_STAB, attackByDistance, m_MeleeCombat.GetHitPos());
366
367 pContinueAttack = false; // reset continueAttack flag
368
369 return true;
370 }
372 else if ( pMovementState.m_iStanceIdx == DayZPlayerConstants.STANCEIDX_RAISEDCROUCH )
373 {
374 if (hcm)
375 {
376 hcm.ForceStance(DayZPlayerConstants.STANCEIDX_RAISEDERECT);
377 pContinueAttack = true;
378 return false;
379 }
380 }
381
382 return false;
383 }
384
386 protected bool HandleInitialMeleeErc(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
387 {
388 //Debug.MeleeLog(m_Player, "HandleInitialMeleeErc[1]");
389
391 m_MeleeCombat.Update(itemInHands, m_HitType);
392
393 //Debug.MeleeLog(m_Player, string.Format("HandleInitialMeleeErc[2] %1", EnumTools.EnumToString(EMeleeHitType, m_HitType)));
394
395 EntityAI target;
396 EMeleeTargetType targetType;
397 GetTargetData(target, targetType);
398 float attackByDistance = GetAttackTypeByDistanceToTarget(target, targetType);
399
400 // finisher attack hittype override
401 int finisherType = m_MeleeCombat.GetFinisherType();
402 if (finisherType != -1)
403 {
404 int animationType = DetermineFinisherAnimation(finisherType);
405 if (animationType > -1)
406 {
407 //Debug.MeleeLog(m_Player, string.Format("HandleInitialMeleeErc[3a] target=%1, finisherType=%2, animationType=%3, hitPositionWS=%4", target, finisherType, animationType, m_MeleeCombat.GetHitPos().ToString()));
408 m_Player.StartCommand_Melee2(target, animationType, attackByDistance, m_MeleeCombat.GetHitPos());
409 }
410 else
411 {
412 //Debug.MeleeLog(m_Player, string.Format("HandleInitialMeleeErc[3b] target=%1, finisherType=%2, animationType=%3, hitPositionWS=%4", target, finisherType, (m_HitType == EMeleeHitType.HEAVY).ToString(), m_MeleeCombat.GetHitPos().ToString()));
413 m_Player.StartCommand_Melee2(target, m_HitType == EMeleeHitType.HEAVY, attackByDistance, m_MeleeCombat.GetHitPos());
414 }
415
416 m_HitType = finisherType;
417 target.SetBeingBackstabbed(finisherType);
418 }
419 else
420 {
421 //Debug.MeleeLog(m_Player, string.Format("HandleInitialMeleeErc[3d] target=%1, animationType=%2, hitPositionWS=%3", target, (m_HitType == EMeleeHitType.HEAVY).ToString(), m_MeleeCombat.GetHitPos().ToString()));
422 m_Player.StartCommand_Melee2(target, m_HitType == EMeleeHitType.HEAVY, attackByDistance, m_MeleeCombat.GetHitPos());
423 }
424
425 if (m_HitType == EMeleeHitType.HEAVY)
426 {
428 if (m_Player.GetBrokenLegs() == eBrokenLegs.BROKEN_LEGS)
429 {
430 m_Player.m_ShockHandler.SetShock(PlayerConstants.BROKEN_LEGS_HEAVY_MELEE_SHOCK);
431 m_Player.m_ShockHandler.CheckValue(true);
432 }
433 }
434 else
435 {
437 if (m_Player.GetBrokenLegs() == eBrokenLegs.BROKEN_LEGS)
438 {
439 m_Player.m_ShockHandler.SetShock(PlayerConstants.BROKEN_LEGS_LIGHT_MELEE_SHOCK);
440 m_Player.m_ShockHandler.CheckValue(true);
441 }
442 }
443
445
447
448 return true;
449 }
450
452 protected bool HandleProneKick(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
453 {
454 HumanCommandWeapons hcw = m_Player.GetCommandModifier_Weapons();
455
456 float hcw_angle = hcw.GetBaseAimingAngleLR();
459 if ( ( hcw_angle < -90 || hcw_angle > 90 ) && m_Player.GetBrokenLegs() != eBrokenLegs.BROKEN_LEGS )
460 {
461 // targetting
463 m_MeleeCombat.Update(itemInHands, m_HitType);
464
465 EntityAI target;
466 EMeleeTargetType targetType;
467 GetTargetData(target, targetType);
468 float attackByDistance = GetAttackTypeByDistanceToTarget(target, targetType);
469
470 // command
471 m_Player.StartCommand_Melee2(target, false, attackByDistance, m_MeleeCombat.GetHitPos());
474
475 return true;
476 }
477
478 return false;
479 }
480
482 protected bool HandleSprintAttack(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
483 {
485 m_HitType = EMeleeHitType.SPRINT;
486 m_MeleeCombat.Update(itemInHands, m_HitType);
487
488 EntityAI target;
489 EMeleeTargetType targetType;
490 GetTargetData(target, targetType);
491 float attackByDistance = GetAttackTypeByDistanceToTarget(target, targetType);
492
494 //Debug.MeleeLog(m_Player, string.Format("HandleSprintAttack[1] target=%1, animationType=%2, hitPositionWS=%3", target, false, m_MeleeCombat.GetHitPos().ToString()));
495
496 m_Player.StartCommand_Melee2(target, EMeleeHitType.HEAVY, attackByDistance, m_MeleeCombat.GetHitPos());
499
500 return true;
501 }
502
504 protected bool HandleComboHit(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
505 {
506 //Debug.MeleeLog(m_Player, "HandleComboHit::");
507 EMeleeHitType hitType;
508
510 if (itemInHands && itemInHands.IsWeapon())
511 hitType = GetAttackTypeByWeaponAttachments(itemInHands);
512 else
513 hitType = GetAttackTypeFromInputs(pInputs);
514
516 if (hitType == EMeleeHitType.NONE)
517 return false;
518
520 if (m_MeleeCombat.GetFinisherType() > -1)
521 return false;
522
523 bool isHeavy = (hitType == EMeleeHitType.HEAVY || hitType == EMeleeHitType.WPN_STAB);
524 EMeleeHitType previousHitType = m_HitType;
525
527 if (!m_WasPreviousHitProcessed && previousHitType != EMeleeHitType.HEAVY && isHeavy)
528 {
529 return false;
530 }
531
532 m_HitType = hitType;
533
535 //Debug.MeleeLog(m_Player, string.Format("HandleComboHit:: %1", EnumTools.EnumToString(EMeleeHitType, m_HitType)));
536 m_MeleeCombat.Update(itemInHands, m_HitType);
537
538 EntityAI target;
539 EMeleeTargetType targetType;
540 GetTargetData(target, targetType);
541 float attackByDistance = GetAttackTypeByDistanceToTarget(target, targetType);
542
544 m_Player.GetCommand_Melee2().ContinueCombo(isHeavy, attackByDistance, target, m_MeleeCombat.GetHitPos());
546
548 if (m_Player.GetBrokenLegs() == eBrokenLegs.BROKEN_LEGS)
549 {
550 float shock = PlayerConstants.BROKEN_LEGS_HEAVY_MELEE_SHOCK;
551
552 if (!isHeavy)
553 shock = PlayerConstants.BROKEN_LEGS_LIGHT_MELEE_SHOCK;
554
555 m_Player.m_ShockHandler.SetShock(PlayerConstants.BROKEN_LEGS_HEAVY_MELEE_SHOCK);
556 m_Player.m_ShockHandler.CheckValue(true);
557 }
558
560 switch (m_HitType)
561 {
562 case EMeleeHitType.HEAVY:
563 case EMeleeHitType.SPRINT:
564 case EMeleeHitType.WPN_STAB:
565 case EMeleeHitType.WPN_HIT_BUTTSTOCK:
566 case EMeleeHitType.WPN_HIT:
568 break;
569 default:
571 break;
572 }
573
574 return true;
575 }
576
577 protected void EvaluateHit(InventoryItem weapon)
578 {
579 EntityAI target = m_MeleeCombat.GetTargetEntity();
580
581 if (target)
582 {
583 if (target.IsInherited(DayZPlayer))
584 {
585 EvaluateHit_Player(weapon, target);
586 }
587 else if (target.IsInherited(DayZInfected))
588 {
589 EvaluateHit_Infected(weapon, target);
590 }
591 else if (target.GetMeleeTargetType() == EMeleeTargetType.NONALIGNABLE)
592 {
593 EvaluateHit_NonAlignableObjects(weapon, target);
594 }
595 else
596 {
597 EvaluateHit_Common(weapon, target);
598 }
599
600 m_MeleeCombat.CheckMeleeItem();
601 }
602 }
603
604 protected void EvaluateHit_Player(InventoryItem weapon, Object target)
605 {
606 int hitZoneIdx = m_MeleeCombat.GetHitZoneIdx();
607 int weaponMode = m_MeleeCombat.GetWeaponMode();
608 int forcedWeaponMode = -1;
609 vector hitPosWS;
610 bool forcedDummy = false;
611
612 PlayerBase targetPlayer = PlayerBase.Cast(target);
614 if (targetPlayer)
615 {
616 vector targetPos = targetPlayer.GetPosition();
617 vector agressorPos = m_Player.GetPosition();
618
619 // We get the angle from which an infected hit the blocking player
620 float hitAngle = Math.RAD2DEG * Math.AbsFloat(Math3D.AngleFromPosition(targetPos, MiscGameplayFunctions.GetHeadingVector(targetPlayer), agressorPos));
621
623 if (targetPlayer.GetMeleeFightLogic() && targetPlayer.GetMeleeFightLogic().IsInBlock() && hitAngle <= GameConstants.PVP_MAX_BLOCKABLE_ANGLE)
624 {
625 if (weaponMode > 0)
626 {
627 forcedWeaponMode = --weaponMode; // Heavy -> Light shift
628 }
629 else
630 forcedDummy = true; // dummy hits, cannot shift lower than 0
631 }
632 }
633
634 EvaluateHit_Common(weapon, target, forcedDummy, forcedWeaponMode);
635 }
636
637 protected void EvaluateHit_Infected(InventoryItem weapon, Object target)
638 {
639 //If the finisher attack haven't been performed, then use normal hit
640 if (!EvaluateFinisherAttack(weapon, target))
641 EvaluateHit_Common(weapon, target);
642 }
643
645 protected bool EvaluateFinisherAttack(InventoryItem weapon, Object target)
646 {
647 //Debug.MeleeLog(m_Player, string.Format("EvaluateFinisherAttack[1] target=%1, hitPos=%2, hitZoneIdx=%3, finisherType=%4", m_MeleeCombat.GetTargetEntity(), m_MeleeCombat.GetHitPos().ToString(), m_MeleeCombat.GetHitZoneIdx(), m_MeleeCombat.GetFinisherType()));
648
649 if (m_MeleeCombat.GetFinisherType() > -1)
650 {
651 if (GetGame().IsServer())
652 DamageSystem.CloseCombatDamage(m_Player, target, m_MeleeCombat.GetHitZoneIdx(), DetermineFinisherAmmo(m_MeleeCombat.GetFinisherType()), m_MeleeCombat.GetHitPos(), ProcessDirectDamageFlags.NO_ATTACHMENT_TRANSFER);
653
654 return true;
655 }
656
657 return false;
658 }
659
660 protected void EvaluateHit_Common(InventoryItem weapon, Object target, bool forcedDummy=false, int forcedWeaponMode = -1)
661 {
662 int hitZoneIdx = m_MeleeCombat.GetHitZoneIdx();
663 int weaponMode = m_MeleeCombat.GetWeaponMode();
664 vector hitPosWS;
665 string ammo;
666
667 if (forcedWeaponMode > -1)
668 weaponMode = forcedWeaponMode;
669
670 EntityAI targetEntity = EntityAI.Cast(target);
671
673 if (!DummyHitSelector(m_HitType, ammo) && !forcedDummy)
674 {
676 if (hitZoneIdx >= 0)
677 {
678 hitPosWS = targetEntity.ModelToWorld(targetEntity.GetDefaultHitPosition());
679
680 if (WeaponDestroyedCheck(weapon, ammo))
681 {
682 DamageSystem.CloseCombatDamage(m_Player, target, hitZoneIdx, ammo, hitPosWS);
683 //Debug.MeleeLog(m_Player, string.Format("EvaluateHit_Common[a]::CloseCombatDamage:: target: %1, hitzone: %2, ammo: %3", target, hitZoneIdx, ammo));
684 }
685 else
686 {
687 m_Player.ProcessMeleeHit(weapon, weaponMode, target, hitZoneIdx, hitPosWS);
688 //Debug.MeleeLog(m_Player, string.Format("EvaluateHit_Common[b]::ProcessMeleeHit:: target: %1, hitzone: %2, meleeMode: %3, forcedWeaponMode:%4", target, hitZoneIdx, weaponMode));
689 }
690 }
691 }
692 else
693 {
695 if (GetGame().IsServer() && targetEntity)
696 {
698 hitPosWS = targetEntity.ModelToWorld(targetEntity.GetDefaultHitPosition());
699 DamageSystem.CloseCombatDamage(m_Player, target, hitZoneIdx, ammo, hitPosWS);
700 //Debug.MeleeLog(m_Player, string.Format("EvaluateHit_Common[c]::CloseCombatDamage:: target: %1, hitzone: %2, meleeMode: %3, ammo: %4", target, hitZoneIdx, weaponMode, ammo));
701 }
702 }
703 }
704
706 {
707 int hitZoneIdx = m_MeleeCombat.GetHitZoneIdx();
708 vector hitPosWS;
709 string ammo;
710
711 if (hitZoneIdx >= 0)
712 {
713 if (WeaponDestroyedCheck(weapon,ammo))
714 DamageSystem.CloseCombatDamage(m_Player, target, hitZoneIdx, ammo, m_MeleeCombat.GetHitPos());
715 else
716 m_Player.ProcessMeleeHit(weapon, m_MeleeCombat.GetWeaponMode(), target, hitZoneIdx, m_MeleeCombat.GetHitPos());
717 }
718
719 return;
720 }
721
722 bool WeaponDestroyedCheck(InventoryItem weapon, out string ammo)
723 {
724 if (!weapon)
725 return false;
726
727 Weapon_Base firearm = Weapon_Base.Cast(weapon);
728 ItemBase bayonet = ItemBase.Cast(weapon.GetInventory().FindAttachment(weapon.GetBayonetAttachmentIdx()));
729
730 if ( firearm && bayonet && bayonet.IsRuined() )
731 {
732 ammo = bayonet.GetRuinedMeleeAmmoType();
733 return true;
734 }
735 else if (weapon.IsRuined())
736 {
737 ammo = weapon.GetRuinedMeleeAmmoType();
738 return true;
739 }
740 else
741 {
742 return false;
743 }
744 }
745
746 protected void GetTargetData(out EntityAI target, out EMeleeTargetType targetType)
747 {
748 target = m_MeleeCombat.GetTargetEntity();
749 targetType = EMeleeTargetType.ALIGNABLE;
750
751 // If there is no hitzone defined, then we won't be able to hit the target anyways..
752 if (m_MeleeCombat.GetHitZoneIdx() < 0)
753 {
754 target = null;
755 }
756
757 if ( target )
758 {
759 targetType = target.GetMeleeTargetType();
760 }
761
763 if ( targetType == EMeleeTargetType.NONALIGNABLE )
764 {
765 target = null;
766 }
767 }
768
770 protected bool DummyHitSelector(EMeleeHitType hitType, out string ammoType)
771 {
772 switch (hitType)
773 {
775 case EMeleeHitType.KICK:
776 ammoType = DUMMY_HEAVY_AMMO;
777 return true;
778 break;
779 }
780
781 ammoType = DUMMY_LIGHT_AMMO;
782
783 return false;
784 }
785
787 protected bool IsBehindEntity(int angle, DayZPlayer source, Object target)
788 {
789 return false;
790 }
791
792 protected void SetCooldown(float time, EFightLogicCooldownCategory cooldownCategory)
793 {
795 if ( m_CooldownTimers.Get(cooldownCategory).IsRunning() )
796 {
797 m_CooldownTimers.Get(cooldownCategory).Stop();
798 }
799
801 Param1<int> param = new Param1<int>(cooldownCategory);
802 m_CooldownTimers.Get(cooldownCategory).Run(time, this, "ResetCooldown", param);
803 }
804
805 protected void ResetCooldown(EFightLogicCooldownCategory cooldownCategory)
806 {
807 switch (cooldownCategory)
808 {
810 m_IsEvading = false;
811 break;
812 }
813 }
814
815 protected void EnableControls();
816 protected void DisableControls();
817
818 protected void DamageHands(DayZPlayer DZPlayer, ClothingBase gloves, InventoryItem itemInHands)
819 {
820 EntityAI target = m_MeleeCombat.GetTargetEntity();
821
822 //We did not hit anything
823 if (itemInHands || !target || !DZPlayer)
824 return;
825
826 //Check if server side
827 if (GetGame().IsServer())
828 {
829 int randNum;
830
831 //If gloves, damage gloves
832 if (gloves && gloves.GetHealthLevel() < GameConstants.STATE_RUINED)
833 {
834 gloves.DecreaseHealth("", "", 1);
835 }
836 else
837 {
838 //Do not add bleeding if hitting player, zombie or animal
839 if (PlayerBase.Cast(target) || DayZCreatureAI.Cast(target))
840 return;
841
842 BleedingSourcesManagerServer bleedingManager;
843
844 //We don't inflict bleeding to hands when kicking
845 if (m_HitType != EMeleeHitType.KICK)
846 {
847 //Random bleeding source
848 randNum = Math.RandomIntInclusive(1, 15);
849 switch (randNum)
850 {
851 case 1:
852 if (m_Player)
853 {
854 bleedingManager = m_Player.GetBleedingManagerServer();
855 if (bleedingManager)
856 bleedingManager.AttemptAddBleedingSourceBySelection("RightForeArmRoll");
857 }
858 break;
859
860 case 2:
861 if (m_Player)
862 {
863 bleedingManager = m_Player.GetBleedingManagerServer();
864 if (bleedingManager)
865 bleedingManager.AttemptAddBleedingSourceBySelection("LeftForeArmRoll");
866 }
867 break;
868 }
869 }
870 else
871 {
872 //Random bleeding source
873 randNum = Math.RandomIntInclusive(1, 15);
874 //We only add bleeding to left foot as character kicks with left foot
875 switch (randNum)
876 {
877 case 1:
878 if (m_Player)
879 {
880 bleedingManager = m_Player.GetBleedingManagerServer();
881 if (bleedingManager)
882 bleedingManager.AttemptAddBleedingSourceBySelection("LeftToeBase");
883 }
884 break;
885
886 case 2:
887 if (m_Player)
888 {
889 bleedingManager = m_Player.GetBleedingManagerServer();
890 if (bleedingManager)
891 bleedingManager.AttemptAddBleedingSourceBySelection("LeftFoot");
892 }
893 break;
894 }
895 }
896 }
897 }
898 }
899
901 int DetermineFinisherAnimation(int finisher_type)
902 {
903 int animation = -1;
904
905 switch (finisher_type)
906 {
907 case EMeleeHitType.FINISHER_LIVERSTAB:
908 animation = HumanCommandMelee2.HIT_TYPE_FINISHER;
909 break;
910
911 case EMeleeHitType.FINISHER_NECKSTAB:
912 animation = HumanCommandMelee2.HIT_TYPE_FINISHER_NECK;
913 break;
914 }
915
916 return animation;
917 }
918
920 string DetermineFinisherAmmo(int finisher_type)
921 {
922 string ret = "";
923
924 switch (finisher_type)
925 {
926 case EMeleeHitType.FINISHER_NECKSTAB:
927 ret = "FinisherHitNeck";
928 break;
929
930 default:
931 ret = "FinisherHit";
932 break;
933 }
934
935 return ret;
936 }
937
938 protected bool IsShortDistance(EntityAI pTarget, float pDistanceSq)
939 {
940 return pTarget && (vector.DistanceSq(m_Player.GetPosition(), m_MeleeCombat.GetHitPos()) <= pDistanceSq) || (vector.DistanceSq(m_Player.GetBonePositionWS(m_Player.GetBoneIndexByName("Head")), m_MeleeCombat.GetHitPos()) <= pDistanceSq);
941 }
942
946 protected bool m_IsFinisher;
947
948 int GetFinisherType(InventoryItem weapon, EntityAI target)
949 {
950 return -1;
951 }
952
953 bool IsHitTypeFinisher(int type)
954 {
955 return false;
956 }
957
959 {
960 return -1;
961 }
962}
do not process rotations !
Definition dayzanimal.c:654
void DepleteStamina(EStaminaModifiers modifier, float dT=-1)
bool CanConsumeStamina(EStaminaConsumers consumer)
Implementations only! - used on PlayerBase.
DayZPlayerImplementMeleeCombat GetMeleeCombat()
bool IsFighting()
HumanInventory... with FSM (synchronous, no anims)
Definition enmath.c:7
Mission class.
Definition gameplay.c:687
override Widget Init()
Definition dayzgame.c:127
DayZPlayerConstants
defined in C++
Definition dayzplayer.c:602
DayZPlayerImplement m_DZPlayer
Parent.
EMeleeHitType m_HitType
Hit type of the most recent attack.
int DetermineSpecificFinisherType(ItemBase weapon)
bool HandleProneKick(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
kick from raised pne
void EvaluateHit_Player(InventoryItem weapon, Object target)
void EnableControls()
bool IsShortDistance(EntityAI pTarget, float pDistanceSq)
EFightLogicCooldownCategory
Light / Heavy punches.
void DamageHands(DayZPlayer DZPlayer, ClothingBase gloves, InventoryItem itemInHands)
void ~DayZPlayerMeleeFightLogic_LightHeavy()
ref DayZPlayerImplementMeleeCombat m_MeleeCombat
bool HandleHitEvent(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
Handle the event that our melee hit something.
EMeleeHitType GetAttackTypeFromInputs(HumanInputController pInputs)
enum EFightLogicCooldownCategory EVADE_COOLDOWN
cooldown timers settings
bool IsBehindEntity(int angle, DayZPlayer source, Object target)
DEPRECATED - moved into DayZPlayerImplementMeleeCombat.
bool EvaluateFinisherAttack(InventoryItem weapon, Object target)
Check and evaluate stealth kill, if applicable.
string DetermineFinisherAmmo(int finisher_type)
Picks a specific finisher ammo fot the hit type. This gets synchronized and guides further behaviour ...
void DayZPlayerMeleeFightLogic_LightHeavy(DayZPlayerImplement player)
bool IsHitTypeFinisher(int type)
const float CLOSE_TARGET_DISTANCE
void EvaluateHit_NonAlignableObjects(InventoryItem weapon, Object target)
void SetBlock(bool block)
ref map< int, ref Timer > m_CooldownTimers
bool HandleInitialFirearmMelee(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
NOTE: Only singular (or first) hits, combo attacks are handled in combo.
int DetermineFinisherAnimation(int finisher_type)
Picks a specific finisher animation. Not used for mounted bayonet stabs.
void GetTargetData(out EntityAI target, out EMeleeTargetType targetType)
bool HandleFightLogic(int pCurrentCommandID, HumanInputController pInputs, EntityAI pEntityInHands, HumanMovementState pMovementState, out bool pContinueAttack)
bool HandleSprintAttack(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
sprint attack in erc stance
bool DummyHitSelector(EMeleeHitType hitType, out string ammoType)
evaluation of hit player vs. player
void EvaluateHit_Infected(InventoryItem weapon, Object target)
float GetAttackTypeByDistanceToTarget(EntityAI pTarget, EMeleeTargetType pTargetType=EMeleeTargetType.ALIGNABLE)
const string DUMMY_HEAVY_AMMO
void EvaluateHit(InventoryItem weapon)
bool HandleComboHit(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
combo hits - when we are already in Melee command and clicking UseButton
EMeleeHitType GetAttackTypeByWeaponAttachments(EntityAI pEntity)
bool WeaponDestroyedCheck(InventoryItem weapon, out string ammo)
const string DUMMY_LIGHT_AMMO
dummy ammo types
void ResetCooldown(EFightLogicCooldownCategory cooldownCategory)
void EvaluateHit_Common(InventoryItem weapon, Object target, bool forcedDummy=false, int forcedWeaponMode=-1)
void DisableControls()
bool HandleInitialMeleeErc(int pCurrentCommandID, HumanInputController pInputs, InventoryItem itemInHands, HumanMovementState pMovementState, out bool pContinueAttack)
First attack in raised erc (light or heavy if modifier is used). Also added support for finishers.
eBrokenLegs
Definition ebrokenlegs.c:2
EMeleeTargetType
EStaminaConsumers
EStaminaModifiers
proto native CGame GetGame()
const int CALL_CATEGORY_SYSTEM
Definition tools.c:8
DayZPlayer m_Player
Definition hand_events.c:42
class BoxCollidingParams component
ComponentInfo for BoxCollidingResult.
ProcessDirectDamageFlags
Definition object.c:2
void SetCooldown(float val)