diff --git a/Subsurface/Content/Characters/Coelanth/coelanth.xml b/Subsurface/Content/Characters/Coelanth/coelanth.xml index 12eabe94d..02a9f67ab 100644 --- a/Subsurface/Content/Characters/Coelanth/coelanth.xml +++ b/Subsurface/Content/Characters/Coelanth/coelanth.xml @@ -15,7 +15,7 @@ - + diff --git a/Subsurface/Content/Characters/Crawler/crawler.xml b/Subsurface/Content/Characters/Crawler/crawler.xml index 42ae65e14..40f74f270 100644 --- a/Subsurface/Content/Characters/Crawler/crawler.xml +++ b/Subsurface/Content/Characters/Crawler/crawler.xml @@ -30,7 +30,7 @@ - + diff --git a/Subsurface/Content/Characters/Endworm/endworm.xml b/Subsurface/Content/Characters/Endworm/endworm.xml index bfcaecdb7..6abd89cdc 100644 --- a/Subsurface/Content/Characters/Endworm/endworm.xml +++ b/Subsurface/Content/Characters/Endworm/endworm.xml @@ -44,12 +44,12 @@ - + - + diff --git a/Subsurface/Content/Characters/Fractalguardian/fractalguardian.xml b/Subsurface/Content/Characters/Fractalguardian/fractalguardian.xml index 32aa58d7c..c7e2aa8ff 100644 --- a/Subsurface/Content/Characters/Fractalguardian/fractalguardian.xml +++ b/Subsurface/Content/Characters/Fractalguardian/fractalguardian.xml @@ -28,12 +28,12 @@ - + - + diff --git a/Subsurface/Content/Characters/Fractalguardian2/fractalguardian2.xml b/Subsurface/Content/Characters/Fractalguardian2/fractalguardian2.xml index 147a5bd7b..e13311179 100644 --- a/Subsurface/Content/Characters/Fractalguardian2/fractalguardian2.xml +++ b/Subsurface/Content/Characters/Fractalguardian2/fractalguardian2.xml @@ -18,7 +18,7 @@ - + @@ -27,7 +27,7 @@ - + diff --git a/Subsurface/Content/Characters/Husk/husk.xml b/Subsurface/Content/Characters/Husk/husk.xml index cad8e14c9..043704787 100644 --- a/Subsurface/Content/Characters/Husk/husk.xml +++ b/Subsurface/Content/Characters/Husk/husk.xml @@ -16,12 +16,22 @@ - - + + + + + + + + + + + + - + @@ -66,14 +76,14 @@ - - - + - - + + + + diff --git a/Subsurface/Content/Characters/Mantis/mantis.xml b/Subsurface/Content/Characters/Mantis/mantis.xml index 76d879210..c5c53f194 100644 --- a/Subsurface/Content/Characters/Mantis/mantis.xml +++ b/Subsurface/Content/Characters/Mantis/mantis.xml @@ -46,7 +46,7 @@ - + diff --git a/Subsurface/Content/Characters/Moloch/moloch.xml b/Subsurface/Content/Characters/Moloch/moloch.xml index 6fb293ffc..c375b9689 100644 --- a/Subsurface/Content/Characters/Moloch/moloch.xml +++ b/Subsurface/Content/Characters/Moloch/moloch.xml @@ -11,7 +11,7 @@ - + diff --git a/Subsurface/Content/Characters/TigerThresher/tigerthresher.xml b/Subsurface/Content/Characters/TigerThresher/tigerthresher.xml index c5cf24d6e..8cd6014e6 100644 --- a/Subsurface/Content/Characters/TigerThresher/tigerthresher.xml +++ b/Subsurface/Content/Characters/TigerThresher/tigerthresher.xml @@ -17,7 +17,7 @@ - + diff --git a/Subsurface/Content/Characters/Watcher/watcher.xml b/Subsurface/Content/Characters/Watcher/watcher.xml index dd12088cc..8c7a24fff 100644 --- a/Subsurface/Content/Characters/Watcher/watcher.xml +++ b/Subsurface/Content/Characters/Watcher/watcher.xml @@ -6,6 +6,7 @@ + @@ -13,8 +14,7 @@ - - + diff --git a/Subsurface/Source/Characters/AI/EnemyAIController.cs b/Subsurface/Source/Characters/AI/EnemyAIController.cs index ca82cf09a..50796b1f6 100644 --- a/Subsurface/Source/Characters/AI/EnemyAIController.cs +++ b/Subsurface/Source/Characters/AI/EnemyAIController.cs @@ -218,24 +218,27 @@ namespace Barotrauma } //steeringManager.SteeringAvoid(deltaTime, 1.0f); - steeringManager.SteeringSeek(attackSimPosition); - + + Limb attackLimb = attackingLimb; //check if any of the limbs is close enough to attack the target if (attackingLimb == null) { foreach (Limb limb in Character.AnimController.Limbs) { - if (limb.attack==null || limb.attack.Type == AttackType.None) continue; + if (limb.attack==null) continue; + attackLimb = limb; + if (ConvertUnits.ToDisplayUnits(Vector2.Distance(limb.SimPosition, attackSimPosition)) > limb.attack.Range) continue; attackingLimb = limb; break; } - return; } - - UpdateLimbAttack(deltaTime, attackingLimb, attackSimPosition); - + if (attackLimb != null) + { + steeringManager.SteeringSeek(attackSimPosition - (attackLimb.SimPosition - SimPosition)); + if (attackingLimb != null) UpdateLimbAttack(deltaTime, attackingLimb, attackSimPosition); + } } private void UpdateCoolDown(Vector2 attackPosition, float deltaTime) @@ -330,84 +333,15 @@ namespace Barotrauma private void UpdateLimbAttack(float deltaTime, Limb limb, Vector2 attackPosition) { - IDamageable damageTarget = null; + var damageTarget = (wallAttackPos != Vector2.Zero && targetEntity != null) ? targetEntity : selectedAiTarget.Entity as IDamageable; - float dist = ConvertUnits.ToDisplayUnits(Vector2.Distance(limb.SimPosition, attackPosition)); + limb.UpdateAttack(deltaTime, attackPosition, damageTarget); - switch (limb.attack.Type) - { - case AttackType.PinchCW: - case AttackType.PinchCCW: - - float dir = (limb.attack.Type == AttackType.PinchCW) ? 1.0f : -1.0f; - - damageTarget = (wallAttackPos != Vector2.Zero && targetEntity != null) ? targetEntity : selectedAiTarget.Entity as IDamageable; - - attackTimer += deltaTime*0.05f; - - if (damageTarget == null) - { - attackTimer = limb.attack.Duration; - break; - } - - if (dist < limb.attack.Range * 0.5f) - { - attackTimer += deltaTime; - limb.body.ApplyTorque(limb.Mass * 50.0f * Character.AnimController.Dir * dir); - - if (attackTimer >= limb.attack.Duration) - { - limb.attack.DoDamage(Character, damageTarget, limb.WorldPosition, 1.0f, (limb.soundTimer <= 0.0f)); - - limb.soundTimer = Limb.SoundInterval; - } - } - - Vector2 diff = attackPosition - limb.SimPosition; - if (diff.LengthSquared() > 0.00001f) - { - limb.body.ApplyLinearImpulse(limb.Mass * 10.0f * - Vector2.Normalize(attackPosition - limb.SimPosition)); - } - - steeringManager.SteeringSeek(attackPosition + (limb.SimPosition-SimPosition), 5.0f); - - break; - case AttackType.Hit: - damageTarget = (wallAttackPos != Vector2.Zero && targetEntity != null) ? targetEntity : selectedAiTarget.Entity as IDamageable; - - if (damageTarget == null) - { - attackTimer = limb.attack.Duration; - break; - } - - if (dist < limb.attack.Range) - { - attackTimer += deltaTime; - limb.body.ApplyForce(limb.Mass * limb.attack.Force * Vector2.Normalize(attackPosition - limb.SimPosition)); - - if (damageTarget is Character && dist= limb.attack.Duration) + if (limb.AttackTimer >= limb.attack.Duration) { wallAttackPos = Vector2.Zero; - attackTimer = 0.0f; - if (Vector2.Distance(limb.SimPosition, attackPosition)<5.0) coolDownTimer = attackCoolDown; - + limb.AttackTimer = 0.0f; + if (Vector2.Distance(limb.SimPosition, attackPosition)<5.0) coolDownTimer = attackCoolDown; } } diff --git a/Subsurface/Source/Characters/Attack.cs b/Subsurface/Source/Characters/Attack.cs index 869daaca4..df02b6d1e 100644 --- a/Subsurface/Source/Characters/Attack.cs +++ b/Subsurface/Source/Characters/Attack.cs @@ -2,6 +2,7 @@ using Barotrauma.Particles; using System; using System.Xml.Linq; +using System.Collections.Generic; namespace Barotrauma @@ -13,11 +14,6 @@ namespace Barotrauma public enum DamageType { None, Blunt, Slash, Burn } - public enum AttackType - { - None, PinchCW, PinchCCW, Hit - } - struct AttackResult { public readonly float Damage; @@ -36,8 +32,6 @@ namespace Barotrauma class Attack { - - public readonly AttackType Type; public readonly float Range; public readonly float Duration; @@ -47,8 +41,12 @@ namespace Barotrauma private readonly float damage; private readonly float bleedingDamage; + private readonly List statusEffects; + public readonly float Force; + public readonly float Torque; + public readonly float TargetForce; private Sound sound; @@ -74,23 +72,8 @@ namespace Barotrauma return (Duration == 0.0f) ? structureDamage : structureDamage * deltaTime; } - - //public Attack(AttackType type, float range,) - //{ - - //} - public Attack(XElement element) { - try - { - Type = (AttackType)Enum.Parse(typeof(AttackType), element.Attribute("type").Value, true); - } - catch - { - Type = AttackType.None; - } - try { DamageType = (DamageType)Enum.Parse(typeof(DamageType), ToolBox.GetAttributeString(element, "damagetype", "None"), true); @@ -106,9 +89,10 @@ namespace Barotrauma bleedingDamage = ToolBox.GetAttributeFloat(element, "bleedingdamage", 0.0f); Force = ToolBox.GetAttributeFloat(element,"force", 0.0f); - TargetForce = ToolBox.GetAttributeFloat(element, "targetforce", 0.0f); + Torque = ToolBox.GetAttributeFloat(element, "torque", 0.0f); + Stun = ToolBox.GetAttributeFloat(element, "stun", 0.0f); string soundPath = ToolBox.GetAttributeString(element, "sound", ""); @@ -123,10 +107,20 @@ namespace Barotrauma priority = ToolBox.GetAttributeFloat(element, "priority", 1.0f); + statusEffects = new List(); + foreach (XElement subElement in element.Elements()) { - if (subElement.Name.ToString().ToLowerInvariant() != "particleemitter") continue; - particleEmitterPrefab = new ParticleEmitterPrefab(subElement); + switch (subElement.Name.ToString().ToLowerInvariant()) + { + case "particleemitter": + particleEmitterPrefab = new ParticleEmitterPrefab(subElement); + break; + case "statuseffect": + statusEffects.Add(StatusEffect.Load(subElement)); + break; + } + } } @@ -143,6 +137,19 @@ namespace Barotrauma sound.Play(1.0f, 500.0f, worldPosition); } + foreach (StatusEffect effect in statusEffects) + { + if (effect.Targets.HasFlag(StatusEffect.TargetType.This) && attacker is Character) + { + effect.Apply(ActionType.OnUse, deltaTime, (Character)attacker, (Character)attacker); + } + if (effect.Targets.HasFlag(StatusEffect.TargetType.Character) && target is Character) + { + effect.Apply(ActionType.OnUse, deltaTime, (Character)target, (Character)target); + } + } + + return target.AddDamage(attacker, worldPosition, this, deltaTime, playSound); } diff --git a/Subsurface/Source/Characters/Limb.cs b/Subsurface/Source/Characters/Limb.cs index 185834879..4ebd2a76e 100644 --- a/Subsurface/Source/Characters/Limb.cs +++ b/Subsurface/Source/Characters/Limb.cs @@ -156,6 +156,8 @@ namespace Barotrauma private float scale; + public float AttackTimer; + //public float Damage //{ // get { return damage; } @@ -223,6 +225,8 @@ namespace Barotrauma refJointIndex = -1; + Vector2 pullJointPos = Vector2.Zero; + if (element.Attribute("type") != null) { try @@ -236,25 +240,26 @@ namespace Barotrauma } - Vector2 jointPos = ToolBox.GetAttributeVector2(element, "pullpos", Vector2.Zero) * scale; - jointPos = ConvertUnits.ToSimUnits(jointPos); + pullJointPos = ToolBox.GetAttributeVector2(element, "pullpos", Vector2.Zero) * scale; + pullJointPos = ConvertUnits.ToSimUnits(pullJointPos); stepOffset = ToolBox.GetAttributeVector2(element, "stepoffset", Vector2.Zero) * scale; stepOffset = ConvertUnits.ToSimUnits(stepOffset); refJointIndex = ToolBox.GetAttributeInt(element, "refjoint", -1); - pullJoint = new FixedMouseJoint(body.FarseerBody, jointPos); - pullJoint.Enabled = false; - pullJoint.MaxForce = ((type == LimbType.LeftHand || type == LimbType.RightHand) ? 400.0f : 150.0f) * body.Mass; - - GameMain.World.AddJoint(pullJoint); } else { type = LimbType.None; } + pullJoint = new FixedMouseJoint(body.FarseerBody, pullJointPos); + pullJoint.Enabled = false; + pullJoint.MaxForce = ((type == LimbType.LeftHand || type == LimbType.RightHand) ? 400.0f : 150.0f) * body.Mass; + + GameMain.World.AddJoint(pullJoint); + steerForce = ToolBox.GetAttributeFloat(element, "steerforce", 0.0f); //maxHealth = Math.Max(ToolBox.GetAttributeFloat(element, "health", 100.0f),1.0f); @@ -484,6 +489,39 @@ namespace Barotrauma //} } + public void ActivateDamagedSprite() + { + damage = 100.0f; + } + + public void UpdateAttack(float deltaTime, Vector2 attackPosition, IDamageable damageTarget) + { + float dist = ConvertUnits.ToDisplayUnits(Vector2.Distance(SimPosition, attackPosition)); + + AttackTimer += deltaTime; + + if (dist < attack.Range * 0.5f) + { + AttackTimer += deltaTime; + body.ApplyTorque(Mass * character.AnimController.Dir * attack.Torque); + + if (AttackTimer >= attack.Duration && damageTarget != null) + { + attack.DoDamage(character, damageTarget, WorldPosition, 1.0f, (soundTimer <= 0.0f)); + + soundTimer = Limb.SoundInterval; + } + } + + Vector2 diff = attackPosition - SimPosition; + if (diff.LengthSquared() > 0.00001f) + { + Vector2 pos = pullJoint == null ? body.SimPosition : pullJoint.WorldAnchorA; + body.ApplyLinearImpulse(Mass * attack.Force * + Vector2.Normalize(attackPosition - SimPosition), pos); + } + + } public void Draw(SpriteBatch spriteBatch) { @@ -492,7 +530,9 @@ namespace Barotrauma body.Dir = Dir; - if (wearingItems.Find(w => w != null && w.HideLimb) == null) + bool hideLimb = wearingItems.Any(w => w != null && w.HideLimb); + + if (!hideLimb) { body.Draw(spriteBatch, sprite, color, null, scale); } @@ -526,7 +566,7 @@ namespace Barotrauma scale, spriteEffect, depth); } - if (damage>0.0f && damagedSprite!=null) + if (damage>0.0f && damagedSprite!=null && !hideLimb) { SpriteEffects spriteEffect = (dir == Direction.Right) ? SpriteEffects.None : SpriteEffects.FlipHorizontally; diff --git a/Subsurface/Source/Characters/StatusEffect.cs b/Subsurface/Source/Characters/StatusEffect.cs index a694f926b..94b8b8c64 100644 --- a/Subsurface/Source/Characters/StatusEffect.cs +++ b/Subsurface/Source/Characters/StatusEffect.cs @@ -173,20 +173,8 @@ namespace Barotrauma break; } } - - //oxygen = ToolBox.GetAttributeFloat(element, "oxygen", 0.0f); - - - //deteriorateOnActive = ToolBox.GetAttributeFloat(element, "deteriorateonactive", 0.0f); - //deteriorateOnUse = ToolBox.GetAttributeFloat(element, "deteriorateonuse", 0.0f); } - - //public virtual void Apply(ActionType type, float deltaTime, Item item, Character Character = null) - //{ - // if (this.type == type) Apply(deltaTime, Character, item); - //} - private bool HasRequiredItems(Entity entity) { if (requiredItems == null) return true;