示例#1
0
        protected ProjectileWeapon(ProjectileWeaponData data, PhysicalUnit owner)
            : base(TimeSpan.FromSeconds(1.0 / data.FireRate), owner)
        {
            _name = data.Name;
            _projectilesPerFire = data.ProjectilesPerFire;
            _projectileInfo = data.ProjectileInfo;
            _spread = data.Spread;

            _contactEffect = _projectileInfo.ContactEffect == null ?
                ProjectileEffect.NullEffect : new ProjectileEffect(_projectileInfo.ContactEffect);
            _proximityEffect = _projectileInfo.ProximityEffect == null ?
                 ProjectileEffect.NullEffect : new ProjectileEffect(_projectileInfo.ProximityEffect);
            _destinationEffect = _projectileInfo.DestinationEffect == null ?
                ProjectileEffect.NullEffect : new ProjectileEffect(_projectileInfo.DestinationEffect);

            _fireParticleEffect = data.FireParticleEffectName == null ?
                null : new ParticleEffect(data.FireParticleEffectName);
            float maxProjLife = data.ProjectileInfo.SecondsToLive +
                Math.Max((float)_contactEffect.Duration.TotalSeconds, (float)_destinationEffect.Duration.TotalSeconds);
            float maxProjectiles = data.FireRate * maxProjLife * data.ProjectilesPerFire;
            maxProjectiles = Math.Max(maxProjectiles, _projectilesPerFire);
            _projectiles = new Projectile[(int)maxProjectiles + 1];
            for (int i = 0; i < _projectiles.Length; i++)
            {
                _projectiles[i] = new Projectile(data.ProjectileInfo.SpriteName);
            }
        }
示例#2
0
        /// <summary>
        /// Apply Gravity on a unit and eat it if close enough
        /// call on each unit during unit update loop
        /// </summary>
        /// <param name="unit">unit to affect. Should be called after updating unit</param>
        public void ApplyToUnit(PhysicalUnit unit, GameTime gameTime)
        {
            float massEaten;

            if (_state != BlackHoleState.Pulling && _state != BlackHoleState.Overdrive)
            {
                return;
            }
            if (_state == BlackHoleState.Pulling)
            {
                unit.ApplyGravity(Gravity, gameTime);
            }
            else if (_state == BlackHoleState.Overdrive)
            {
                unit.FlyToPoint(Position, _overdriveTimer, 2.0f);
            }

            if ((massEaten = unit.EatByBlackHole(Position, _radius)) > 0)
            {
                _capacityUsed += massEaten;
                _particleEffect.IntensityFactor = 1.0f + _capacityUsed / _totalCapacity;
                Gravity.MagnitudeFactor         = (1.0f + _capacityUsed / _totalCapacity);
                if (_capacityUsed > _totalCapacity)
                {
                    goOverdrive();
                }
            }
        }
示例#3
0
文件: Enemy.cs 项目: rcorre/MSH-win8
 public void CheckAndApplyWeaponCollision(PhysicalUnit unit, TimeSpan time)
 {
     if (_meleeWeapon != null)
     {
         _meleeWeapon.CheckAndApplyCollision(unit, time);
     }
 }
示例#4
0
 /// <summary>
 /// Create a new weapon
 /// </summary>
 /// <param name="fireDelay">Time between successive shots</param>
 /// <param name="maxAmmo">Total ammo capacity. Set to 1 for infinite ammo.</param>
 /// <param name="ammoConsumption">Ammo used per shot. Set to 0 for infinite ammo.</param>
 /// <param name="levelWidth">Width of the level in which this weapon is instantiated.</param>
 /// <param name="levelHeight">Height of the level in which this weapon is instantiated.</param>
 public Weapon(TimeSpan fireDelay, int maxAmmo, int ammoConsumption, PhysicalUnit owner)
 {
     _fireDelay = fireDelay;
     _maxAmmo = maxAmmo;
     _currentAmmo = maxAmmo;
     _ammoConsumption = ammoConsumption;
     _owner = owner;
 }
 public HookShot(PhysicalUnit owner)
     : base(TimeSpan.FromSeconds(FIRE_DELAY), 1, 0, owner)
 {
     _hookState = HookState.Idle;
     _hookSprite = new Sprite("HookClaw");
     _chainSprite = new Sprite("HookChain");
     _hookHitRect = new Rectangle(0, 0, (int)_hookSprite.Width, (int)_hookSprite.Height);
 }
        public void CheckAndApplyUnitCollision(PhysicalUnit other)
        {
            if (!Collides)
            {
                return;     //don't check collision if unit shouldn't collide
            }
            //special shattered collision detection
            if (_lifeState == LifeState.Shattered)
            {
                tempRec.Width  = _hitRect.Width / ICE_DIVISIONS;
                tempRec.Height = _hitRect.Height / ICE_DIVISIONS;
                for (int i = 0; i < ICE_DIVISIONS; i++)
                {
                    for (int j = 0; j < ICE_DIVISIONS; j++)
                    {
                        tempRec.X = (int)(_fragments[i, j].Position.X - tempRec.Width / 2);
                        tempRec.Y = (int)(_fragments[i, j].Position.Y - tempRec.Height / 2);
                        if (tempRec.Intersects(other.HitRect))
                        {
                            Vector2 fVel  = _fragments[i, j].Velocity;
                            float   fMass = (float)Mass / (ICE_DIVISIONS * ICE_DIVISIONS);
                            temp            = other.Velocity;
                            other._velocity = (other._velocity * (other.Mass - fMass) + 2 * fMass * fVel) /
                                              (fMass + other.Mass);
                            _fragments[i, j].Velocity = (fVel * (fMass - other.Mass) + 2 * other.Mass * temp) /
                                                        (fMass + other.Mass);
                        }
                    }
                }
                return; //ignore normal collision detection
            }

            //check if fire should be transferred
            float dist = XnaHelper.DistanceBetweenRects(HitRect, other.HitRect);

            if (dist < FIRE_SPREAD_DISTANCE)
            {
                if (_statusEffects.Fire > other._statusEffects.Fire)
                {
                    StatEffect transfer = new StatEffect()
                    {
                        Fire = FIRE_SPREAD_FACTOR * dist / FIRE_SPREAD_DISTANCE * _statusEffects.Fire
                    };
                    other.ApplyStatus(transfer);
                    ApplyStatus(transfer * -FIRE_SPREAD_LOSS);
                }
            }

            if (XnaHelper.RectsCollide(HitRect, other.HitRect))
            {
                temp = other._velocity; //temp is a static reusable vector

                other._velocity = (other._velocity * (other.Mass - this.Mass) + 2 * this.Mass * this._velocity) /
                                  (this.Mass + other.Mass);
                this._velocity = (this._velocity * (this.Mass - other.Mass) + 2 * other.Mass * temp) /
                                 (this.Mass + other.Mass);
            }
        }
示例#7
0
 /// <summary>
 /// Create a new weapon
 /// </summary>
 /// <param name="fireDelay">Time between successive shots</param>
 /// <param name="maxAmmo">Total ammo capacity. Set to 1 for infinite ammo.</param>
 /// <param name="ammoConsumption">Ammo used per shot. Set to 0 for infinite ammo.</param>
 /// <param name="levelWidth">Width of the level in which this weapon is instantiated.</param>
 /// <param name="levelHeight">Height of the level in which this weapon is instantiated.</param>
 public Weapon(WeaponData data, PhysicalUnit owner, string spriteName = null)
 {
     _fireDelay = TimeSpan.FromSeconds(1.0 / data.FireRate);
     _owner = owner;
     if (spriteName != null)
     {
         Sprite = new WeaponSprite(spriteName);
     }
 }
示例#8
0
        public override void CheckAndApplyCollision(PhysicalUnit unit, TimeSpan time)
        {
            if (!unit.Collides)
                return;

            foreach (Projectile p in _projectiles)
            {
                p.CheckAndApplyCollision(unit, time);
            }
        }
示例#9
0
 public void CheckCollisions(GameTime gameTime, PhysicalUnit unit)
 {
     foreach (IConsumable item in _slots)
     {
         if (item is ProjectileWeapon)
         {
             (item as ProjectileWeapon).CheckAndApplyCollision(unit, gameTime.ElapsedGameTime);
         }
     }
 }
示例#10
0
 public override void CheckAndApplyCollision(PhysicalUnit unit, TimeSpan time)
 {
     if (_hookState == HookState.Fired || _hookState == HookState.Retracting)
     {
         if (XnaHelper.RectsCollide(_hookHitRect, unit.HitRect))
         {
             _hookedUnit = unit;
             _hookState = HookState.Attached;
         }
     }
 }
 protected MeleeWeapon(MeleeWeaponData data, PhysicalUnit owner)
     : base(data, owner, data.Name)
 {
     _damage = data.Damage;
     _force = data.Impact;
     _recoil = data.Recoil;
     _hitArc = data.HitArc;
     _range = data.Range;
     _attackParticleEffect = (data.AttackParticleEffect == null) ?
         null : new ParticleEffect(data.AttackParticleEffect);
     _hitParticleEffect = (data.HitParticleEffect == null) ?
         null : new ParticleEffect(data.HitParticleEffect);
 }
示例#12
0
 protected MeleeWeapon(MeleeWeaponData data, PhysicalUnit owner)
     : base(TimeSpan.FromSeconds(1.0 / data.FireRate), owner)
 {
     _damage = data.Damage;
     _force = data.Impact;
     _recoil = data.Recoil;
     _hitArc = data.HitArc;
     _range = data.Range;
     _attackParticleEffect = (data.AttackParticleEffect == null) ?
         null : new ParticleEffect(data.AttackParticleEffect);
     _hitParticleEffect = (data.HitParticleEffect == null) ?
         null : new ParticleEffect(data.HitParticleEffect);
 }
示例#13
0
 public HookShot(PhysicalUnit owner)
     : base(new WeaponData
     {
         Name = "Hookshot",
         FireRate = c_fireRate,
     },
     owner)
 {
     _hookState = HookState.Idle;
     _hookSprite = new Sprite("HookClaw", SpaceGame.graphics.Sprite.SpriteType.Projectile);
     _chainSprite = new Sprite("HookChain", SpaceGame.graphics.Sprite.SpriteType.Projectile);
     _hookHitRect = new Rectangle(0, 0, (int)_hookSprite.Width, (int)_hookSprite.Height);
 }
        public override void CheckAndApplyCollision(PhysicalUnit unit, TimeSpan time)
        {
            if (!_firing || !unit.Collides)
                return;     //don't check collisions if not firing

            float fireAngle = XnaHelper.RadiansFromVector(_fireDirection);
            if (XnaHelper.RectangleIntersectsArc(unit.HitRect, _owner.Center, _range, fireAngle, _hitArc))
            {
                _tempVector = unit.Center - _owner.Center;
                _tempVector.Normalize();
                unit.ApplyImpact(_force * _tempVector, 1);
                unit.ApplyDamage(_damage);
            }
        }
        protected ProjectileWeapon(ProjectileWeaponData data, PhysicalUnit owner)
            : base(TimeSpan.FromSeconds(1.0 / data.FireRate), 
                  data.MaxAmmo,
                  data.AmmoConsumption,
                  owner)
        {
            _maxProjectiles = data.MaxProjectiles;
            _projectiles = new Projectile[_maxProjectiles];
            for (int i = 0; i < _maxProjectiles; i++)
            {
                _projectiles[i] = new Projectile();
                _projectiles[i].ProjectileSprite = new Sprite(data.ProjectileSpriteName);
            }
            _projectileDamage = data.Damage;
            _projectileForce = data.ProjectileForce;
            _recoilForce = data.Recoil;
            _projectileSpeed = data.ProjectileSpeed;
            _projectileAcceleration = data.ProjectileAcceleration;
            _dissipateOnHit = data.DissipateOnHit;
            _projectileSpread = MathHelper.ToRadians(data.ProjectileSpread);
            _projectilesPerFire = data.ProjectilesPerFire;
            _projectileLife = data.ProjectileLife;

            _splashDamage = data.SplashDamage;
            _splashRadius = data.SplashRadius;
            _splashForce = data.SplashForce;

            Sprite projectileSprite = _projectiles[0].ProjectileSprite;

            if (projectileSprite.Width <= _splashRadius * 2)
            {
                _splashScaleRate = (projectileSprite.Width / _splashRadius);
                _splashScaleRate /= (float)projectileSprite.FullAnimationTime.TotalSeconds;
            }

            _hitDetectionRect = new Rectangle(0,0,
               (int)(projectileSprite.Width), (int)projectileSprite.Height);

            if (data.MovementParticleEffect != null)
                _movementParticleEffect = new ParticleEffect(data.MovementParticleEffect);
            if (data.SplashParticleEffect != null)
                _splashParticleEffect = new ParticleEffect(data.SplashParticleEffect);
        }
示例#16
0
        public void CheckAndApplyCollision(PhysicalUnit unit, GameTime gameTime)
        {
            switch (_state)
            {
            case State.Dormant:
                break;

            case State.Appearing:
            case State.Scanning:
                unit.ApplyGravity(_gravity, gameTime);
                break;

            case State.Charging:
                unit.ApplyGravity(_gravity, gameTime);
                if (willCollide(unit.Top, unit.Bottom, unit.Left, unit.Right, gameTime.ElapsedGameTime))
                {
                    unit.ApplyImpact(_velocity, IMPACT_IMPULSE);
                    unit.ApplyDamage(IMPACT_DAMAGE);
                    break;
                }
                break;
            }
        }
        protected UnitSprite(UnitSpriteData data, PhysicalUnit unit)
            : base(data, SpriteType.Unit)
        {
            _unit = unit;
            if (_numStates % 2 == 0)
            {
                throw new Exception(String.Format("UnitSprite {0} has an even number of states along the horizontal axis", data.Name));
            }
            //shoulder positioning
            _unitShoulderOffset = new Vector2(data.ShoulderX, data.ShoulderY);
            _flippedUnitShoulderOffset = new Vector2(-data.ShoulderX, data.ShoulderY);
            _armTexture = Content.Load<Texture2D>(c_armSpritePath + data.SpriteArmData.Name);
            //hand/weapon positioning
            _armShoulderPos = new Vector2(data.SpriteArmData.ShoulderX, data.SpriteArmData.ShoulderY);
            _shoulderToHand = new Vector2(data.SpriteArmData.HandX, data.SpriteArmData.HandY);
            //leg positioning
            _legTexture = Content.Load<Texture2D>(c_legSpritePath + data.SpriteLegData.Name);
            _unitHipOffset = new Vector2(data.HipX, data.HipY);
            _flippedUnitHipOffset = new Vector2(-data.HipX, data.HipY);
            _legOrigin = new Vector2(data.SpriteLegData.HipX, data.SpriteLegData.HipY);
            _flippedLegOrigin = new Vector2(_legTexture.Width - data.SpriteLegData.HipX, data.SpriteLegData.HipY);

            _exhaustOffset = new Vector2(data.ExhaustX, data.ExhaustY);
        }
        public void CheckAndApplyUnitCollision(PhysicalUnit other)
        {
            if (!Collides)
                return;     //don't check collision if unit shouldn't collide
            //special shattered collision detection
            if (_lifeState == LifeState.Shattered)
            {
                tempRec.Width = _hitRect.Width / ICE_DIVISIONS;
                tempRec.Height = _hitRect.Height / ICE_DIVISIONS;
                for (int i = 0; i < ICE_DIVISIONS ; i++)
                    for (int j = 0; j < ICE_DIVISIONS; j++)
                    {
                        tempRec.X = (int)(_fragments[i,j].Position.X - tempRec.Width / 2);
                        tempRec.Y = (int)(_fragments[i,j].Position.Y - tempRec.Height / 2);
                        if (tempRec.Intersects(other.HitRect))
                        {
                            Vector2 fVel = _fragments[i, j].Velocity;
                            float fMass = (float)Mass / (ICE_DIVISIONS * ICE_DIVISIONS);
                            temp = other.Velocity;
                            other._velocity = (other._velocity * (other.Mass - fMass) + 2 * fMass * fVel) /
                                                (fMass + other.Mass);
                            _fragments[i,j].Velocity = (fVel * (fMass - other.Mass) + 2 * other.Mass * temp) /
                                                (fMass + other.Mass);
                        }
                    }
                return; //ignore normal collision detection
            }

            //check if fire should be transferred
            float dist = XnaHelper.DistanceBetweenRects(HitRect, other.HitRect);
            if (dist < FIRE_SPREAD_DISTANCE)
            {
                if (_statusEffects.Fire > other._statusEffects.Fire)
                {
                    StatEffect transfer = new StatEffect() { Fire = FIRE_SPREAD_FACTOR * dist / FIRE_SPREAD_DISTANCE * _statusEffects.Fire };
                    other.ApplyStatus(transfer);
                    ApplyStatus(transfer * -FIRE_SPREAD_LOSS);
                }
            }

            if (XnaHelper.RectsCollide(HitRect, other.HitRect))
            {
                temp = other._velocity; //temp is a static reusable vector

                other._velocity = (other._velocity * (other.Mass - this.Mass) + 2 * this.Mass * this._velocity) /
                                    (this.Mass + other.Mass);
                this._velocity = (this._velocity * (this.Mass - other.Mass) + 2 * other.Mass * temp) /
                                    (this.Mass + other.Mass);
            }
        }
        public void CheckAndApplyUnitCollision(PhysicalUnit other)
        {
            if (!Collides)
                return;     //don't check collision if unit shouldn't collide

            if (XnaHelper.RectsCollide(HitRect, other.HitRect))
            {
                temp = other._velocity; //temp is a static reusable vector

                other._velocity = (other._velocity * (other.Mass - this.Mass) + 2 * this.Mass * this._velocity) /
                                    (this.Mass + other.Mass);
                this._velocity = (this._velocity * (this.Mass - other.Mass) + 2 * other.Mass * temp) /
                                    (this.Mass + other.Mass);
            }
        }
示例#20
0
 public void CheckAndApplyWeaponCollision(PhysicalUnit unit, TimeSpan time)
 {
     if (CurrentWeapon != null)
         CurrentWeapon.CheckAndApplyCollision(unit, time);
 }
 public MeleeWeapon(string weaponName, PhysicalUnit owner)
     : this(DataManager.GetData<MeleeWeaponData>(weaponName), owner)
 {
 }
 public ProjectileWeapon(string weaponName, PhysicalUnit owner)
     : this(ProjectileWeaponData[weaponName], owner)
 {
 }
示例#23
0
 public ThrowableWeapon(string name, PhysicalUnit owner)
     : base(DataDict[name], owner)
 {
     _maxAmmo = DataDict[name].UsesPerStack;
     NumUses = _maxAmmo;
 }
示例#24
0
 /// <summary>
 /// Check if weapon is hitting a target, and apply its affects if so
 /// Call during the update loop on each unit
 /// </summary>
 /// <param name="unit"></param>
 public abstract void CheckAndApplyCollision(PhysicalUnit unit, TimeSpan time);
示例#25
0
 public ProjectileWeapon(string name, PhysicalUnit owner)
     : this(DataDict[name], owner)
 {
 }
 public ThrowableWeapon(string name, PhysicalUnit owner)
     : base(DataManager.GetData<ThrowableWeaponData>(name), owner, null)
 {
     _maxAmmo = DataManager.GetData<ThrowableWeaponData>(name).UsesPerStack;
     NumUses = _maxAmmo;
 }
 /// <summary>
 /// Check if target unit is in range. If so, apply force and damage
 /// </summary>
 /// <param name="effectPos">origin of effect</param>
 /// <param name="target">target unit</param>
 public void TryApply(Vector2 effectPos, PhysicalUnit target, TimeSpan time)
 {
     if (utility.XnaHelper.RectangleIntersectsCircle(target.HitRect, effectPos, _radius))
     {
         tempVec.X = target.Position.X - effectPos.X;
         tempVec.Y = target.Position.Y - effectPos.Y;
         Vector2.Normalize(tempVec);
         float factor = Duration == TimeSpan.Zero ? 1 : (float)time.TotalSeconds / (float)Duration.TotalSeconds;
         target.ApplyForce(_force * factor * tempVec);
         target.ApplyDamage((_damage * factor));
         target.ApplyStatus(_statEffects);
     }
 }
        Vector2 _weaponOrigin; //weapon vectors

        #endregion Fields

        #region Constructors

        public UnitSprite(string name, PhysicalUnit unit)
            : this(DataManager.GetData<UnitSpriteData>(name), unit)
        {
        }
        public void CheckAndApplyCollision(PhysicalUnit u, TimeSpan time)
        {
            if (!u.Collides)
                return;

            switch (_state)
            {
                case State.Dormant:
                    break;
                case State.Moving:
                    if (u.HitRect.Intersects(_hitRect))
                    {
                        if (_penetration != -1)
                        {
                            _penetration -= 1;
                            if (_penetration <= 0)
                                _state = State.JustHit;
                        }
                        u.ApplyImpact(_velocity, _mass);
                    }
                    _proximityEffect.TryApply(_position, u, time);
                    break;
                case State.JustHit:
                    break;
                case State.ApplyContactEffect:
                    _contactEffect.TryApply(_position, u, time);
                    break;
                case State.ReachedDestination:
                    _destinationEffect.TryApply(_position, u, time);
                    break;
                default:
                    break;
            }
        }
 public MeleeWeapon(string weaponName, PhysicalUnit owner)
     : this(MeleeWeaponDataDict[weaponName], owner)
 {
 }
示例#31
0
 /// <summary>
 /// Check if weapon is hitting a target, and apply its affects if so
 /// Call during the update loop on each unit
 /// </summary>
 /// <param name="unit"></param>
 public abstract void CheckAndApplyCollision(PhysicalUnit unit);
 protected virtual void applyProjectileHit(Projectile p, PhysicalUnit unit)
 {
     unit.ApplyForce(p.Velocity / p.Velocity.Length() * _projectileForce);
     unit.ApplyDamage(_projectileDamage);
     if (_dissipateOnHit)
         p.Active = false;
     if (_splashRadius > 0)
     {
         p.ReadyToSplash = true;
         p.Velocity = Vector2.Zero;
         p.ProjectileSprite.PlayAnimation(1);
     }
 }
示例#33
0
 public void CheckAndApplyCollision(PhysicalUnit unit, GameTime gameTime)
 {
     switch (_state)
     {
         case State.Dormant:
             break;
         case State.Appearing:
         case State.Scanning:
             unit.ApplyGravity(_gravity, gameTime);
             break;
         case State.Charging:
             unit.ApplyGravity(_gravity, gameTime);
             if (willCollide(unit.Top, unit.Bottom, unit.Left, unit.Right, gameTime.ElapsedGameTime))
             {
                 unit.ApplyImpact(_velocity, IMPACT_IMPULSE);
                 unit.ApplyDamage(IMPACT_DAMAGE);
                 break;
             }
             break;
     }
 }
示例#34
0
        /// <summary>
        /// Apply Gravity on a unit and eat it if close enough
        /// call on each unit during unit update loop
        /// </summary>
        /// <param name="unit">unit to affect. Should be called after updating unit</param>
        public void ApplyToUnit(PhysicalUnit unit, GameTime gameTime)
        {
            float massEaten;
            if (_state != BlackHoleState.Pulling && _state != BlackHoleState.Overdrive)
                return;
            if (_state == BlackHoleState.Pulling)
            {
                unit.ApplyGravity(Gravity, gameTime);
            }
            else if (_state == BlackHoleState.Overdrive)
            {
                unit.FlyToPoint(Position, _overdriveTimer, 2.0f);
            }

            if ((massEaten = unit.EatByBlackHole(Position, _radius)) > 0)
            {
                _capacityUsed += massEaten;
                _particleEffect.IntensityFactor = 1.0f + _capacityUsed / _totalCapacity;
                Gravity.MagnitudeFactor = (1.0f + _capacityUsed / _totalCapacity);
                if (_capacityUsed > _totalCapacity)
                {
                    goOverdrive();
                }
            }
        }