private void StasisBlast(RealmTime time, Item item, Position target, ActivateEffect eff) { var pkts = new List <Packet> { new ShowEffect() { EffectType = EffectType.Concentrate, TargetObjectId = Id, Pos1 = target, Pos2 = new Position() { X = target.X + 3, Y = target.Y }, Color = new ARGB(0xffffffff) } }; Owner.AOE(target, 3, false, enemy => { if (enemy.HasConditionEffect(ConditionEffects.StasisImmune)) { pkts.Add(new Notification() { ObjectId = enemy.Id, Color = new ARGB(0xff00ff00), Message = "Immune" }); } else if (!enemy.HasConditionEffect(ConditionEffects.Stasis)) { enemy.ApplyConditionEffect(ConditionEffectIndex.Stasis, eff.DurationMS); Owner.Timers.Add(new WorldTimer(eff.DurationMS, (world, t) => enemy.ApplyConditionEffect(ConditionEffectIndex.StasisImmune, 3000))); pkts.Add(new Notification() { ObjectId = enemy.Id, Color = new ARGB(0xffff0000), Message = "Stasis" }); } }); BroadcastSync(pkts, p => this.DistSqr(p) < RadiusSqr); }
void Activate(RealmTime time, Item item, Position target) { MP -= item.MpCost; foreach (var eff in item.ActivateEffects) { switch (eff.Effect) { case ActivateEffects.BulletNova: { var prjDesc = item.Projectiles[0]; //Assume only one Packet[] batch = new Packet[21]; uint s = Random.CurrentSeed; Random.CurrentSeed = (uint)(s * time.tickTimes); for (int i = 0; i < 20; i++) { Projectile proj = CreateProjectile(prjDesc, item.ObjectType, (int)statsMgr.GetAttackDamage(prjDesc.MinDamage, prjDesc.MaxDamage), time.tickTimes, target, (float)(i * (Math.PI * 2) / 20)); Owner.EnterWorld(proj); FameCounter.Shoot(proj); batch[i] = new ShootPacket() { BulletId = proj.ProjectileId, OwnerId = Id, ContainerType = item.ObjectType, Position = target, Angle = proj.Angle, Damage = (short)proj.Damage }; } Random.CurrentSeed = s; batch[20] = new ShowEffectPacket() { EffectType = EffectType.Trail, PosA = target, TargetId = Id, Color = new ARGB(0xFFFF00AA) }; BroadcastSync(batch, p => this.Dist(p) < 25); } break; case ActivateEffects.Shoot: { ActivateShoot(time, item, target); } break; case ActivateEffects.StatBoostSelf: { int idx = -1; switch ((StatsType)eff.Stats) { case StatsType.MaximumHP: idx = 0; break; case StatsType.MaximumMP: idx = 1; break; case StatsType.Attack: idx = 2; break; case StatsType.Defense: idx = 3; break; case StatsType.Speed: idx = 4; break; case StatsType.Vitality: idx = 5; break; case StatsType.Wisdom: idx = 6; break; case StatsType.Dexterity: idx = 7; break; } int s = eff.Amount; Boost[idx] += s; UpdateCount++; Owner.Timers.Add(new WorldTimer(eff.DurationMS, (world, t) => { Boost[idx] -= s; UpdateCount++; })); BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.Potion, TargetId = Id, Color = new ARGB(0xffffffff) }, null); } break; case ActivateEffects.StatBoostAura: { int idx = -1; switch ((StatsType)eff.Stats) { case StatsType.MaximumHP: idx = 0; break; case StatsType.MaximumMP: idx = 1; break; case StatsType.Attack: idx = 2; break; case StatsType.Defense: idx = 3; break; case StatsType.Speed: idx = 4; break; case StatsType.Vitality: idx = 5; break; case StatsType.Wisdom: idx = 6; break; case StatsType.Dexterity: idx = 7; break; } int s = eff.Amount; this.AOE(eff.Range / 2, true, player => { (player as Player).Boost[idx] += s; player.UpdateCount++; Owner.Timers.Add(new WorldTimer(eff.DurationMS, (world, t) => { (player as Player).Boost[idx] -= s; player.UpdateCount++; })); }); BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffffffff), PosA = new Position() { X = eff.Range / 2 } }, p => this.Dist(p) < 25); } break; case ActivateEffects.ConditionEffectSelf: { ApplyConditionEffect(new ConditionEffect() { Effect = eff.ConditionEffect.Value, DurationMS = eff.DurationMS }); BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffffffff), PosA = new Position() { X = 1 } }, p => this.Dist(p) < 25); } break; case ActivateEffects.ConditionEffectAura: { this.AOE(eff.Range / 2, true, player => { player.ApplyConditionEffect(new ConditionEffect() { Effect = eff.ConditionEffect.Value, DurationMS = eff.DurationMS }); }); uint color = 0xffffffff; if (eff.ConditionEffect.Value == ConditionEffectIndex.Damaging) { color = 0xffff0000; } BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(color), PosA = new Position() { X = eff.Range / 2 } }, p => this.Dist(p) < 25); } break; case ActivateEffects.Heal: { List <Packet> pkts = new List <Packet>(); ActivateHealHp(this, eff.Amount, pkts); BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.HealNova: { List <Packet> pkts = new List <Packet>(); this.AOE(eff.Range / 2, true, player => { ActivateHealHp(player as Player, eff.Amount, pkts); }); pkts.Add(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffffffff), PosA = new Position() { X = eff.Range / 2 } }); BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.Magic: { List <Packet> pkts = new List <Packet>(); ActivateHealMp(this, eff.Amount, pkts); BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.MagicNova: { List <Packet> pkts = new List <Packet>(); this.AOE(eff.Range / 2, true, player => { ActivateHealMp(player as Player, eff.Amount, pkts); }); pkts.Add(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffffffff), PosA = new Position() { X = eff.Range / 2 } }); BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.Teleport: { Move(target.X, target.Y); UpdateCount++; BroadcastSync(new Packet[] { new GotoPacket() { ObjectId = Id, Position = new Position() { X = X, Y = Y } }, new ShowEffectPacket() { EffectType = EffectType.Teleport, TargetId = Id, PosA = new Position() { X = X, Y = Y }, Color = new ARGB(0xFFFFFFFF) } }, p => this.Dist(p) < 25); } break; case ActivateEffects.VampireBlast: { List <Packet> pkts = new List <Packet>(); pkts.Add(new ShowEffectPacket() { EffectType = EffectType.Trail, TargetId = Id, PosA = target, Color = new ARGB(0xFFFF0000) }); pkts.Add(new AOEPacket() { Position = target, Radius = eff.Radius, Damage = (ushort)eff.TotalDamage, EffectDuration = 0, Effects = 0, OriginType = item.ObjectType }); int totalDmg = 0; var enemies = new List <Enemy>(); Owner.AOE(target, eff.Radius, false, enemy => { enemies.Add(enemy as Enemy); totalDmg += (enemy as Enemy).Damage(this, time, eff.TotalDamage, false); }); var players = new List <Player>(); this.AOE(eff.Radius, true, player => { players.Add(player as Player); ActivateHealHp(player as Player, totalDmg, pkts); }); Random rand = new System.Random(); for (int i = 0; i < 5; i++) { Enemy a = enemies[rand.Next(0, enemies.Count)]; Player b = players[rand.Next(0, players.Count)]; pkts.Add(new ShowEffectPacket() { EffectType = EffectType.Flow, TargetId = b.Id, PosA = new Position() { X = a.X, Y = a.Y }, Color = new ARGB(0xffffffff) }); } BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.Trap: { BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.Throw, Color = new ARGB(0xff9000ff), TargetId = Id, PosA = target }, p => this.Dist(p) < 25); Owner.Timers.Add(new WorldTimer(1500, (world, t) => { Trap trap = new Trap( this, eff.Radius, eff.TotalDamage, eff.ConditionEffect ?? ConditionEffectIndex.Slowed, eff.EffectDuration); trap.Move(target.X, target.Y); world.EnterWorld(trap); })); } break; case ActivateEffects.StasisBlast: { List <Packet> pkts = new List <Packet>(); pkts.Add(new ShowEffectPacket() { EffectType = EffectType.Concentrate, TargetId = Id, PosA = target, PosB = new Position() { X = target.X + 3, Y = target.Y }, Color = new ARGB(0xffffffff) }); Owner.AOE(target, 3, false, enemy => { if (enemy.HasConditionEffect(ConditionEffects.StasisImmune)) { pkts.Add(new NotificationPacket() { ObjectId = enemy.Id, Color = new ARGB(0xff00ff00), Text = "Immune" }); } else if (!enemy.HasConditionEffect(ConditionEffects.Stasis)) { enemy.ApplyConditionEffect( new ConditionEffect() { Effect = ConditionEffectIndex.Stasis, DurationMS = eff.DurationMS }, new ConditionEffect() { Effect = ConditionEffectIndex.Confused, DurationMS = eff.DurationMS } ); Owner.Timers.Add(new WorldTimer(eff.DurationMS, (world, t) => { enemy.ApplyConditionEffect(new ConditionEffect() { Effect = ConditionEffectIndex.StasisImmune, DurationMS = 3000 } ); } )); pkts.Add(new NotificationPacket() { ObjectId = enemy.Id, Color = new ARGB(0xffff0000), Text = "Stasis" }); } }); BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.Decoy: { var decoy = new Decoy(this, eff.DurationMS, statsMgr.GetSpeed()); decoy.Move(X, Y); Owner.EnterWorld(decoy); } break; case ActivateEffects.Lightning: { Enemy start = null; double angle = Math.Atan2(target.Y - Y, target.X - X); double diff = Math.PI / 3; Owner.AOE(target, 6, false, enemy => { if (!(enemy is Enemy)) { return; } var x = Math.Atan2(enemy.Y - Y, enemy.X - X); if (Math.Abs(angle - x) < diff) { start = enemy as Enemy; diff = Math.Abs(angle - x); } }); if (start == null) { break; } Enemy current = start; Enemy[] targets = new Enemy[eff.MaxTargets]; for (int i = 0; i < targets.Length; i++) { targets[i] = current; Enemy next = current.GetNearestEntity(8, false, enemy => enemy is Enemy && Array.IndexOf(targets, enemy) == -1 && this.Dist(enemy) <= 6) as Enemy; if (next == null) { break; } else { current = next; } } List <Packet> pkts = new List <Packet>(); for (int i = 0; i < targets.Length; i++) { if (targets[i] == null) { break; } Entity prev = i == 0 ? (Entity)this : targets[i - 1]; targets[i].Damage(this, time, eff.TotalDamage, false); if (eff.ConditionEffect != null) { targets[i].ApplyConditionEffect(new ConditionEffect() { Effect = eff.ConditionEffect.Value, DurationMS = (int)(eff.EffectDuration * 1000) }); } pkts.Add(new ShowEffectPacket() { EffectType = EffectType.Lightning, TargetId = prev.Id, Color = new ARGB(0xffff0088), PosA = new Position() { X = targets[i].X, Y = targets[i].Y }, PosB = new Position() { X = 350 } }); } BroadcastSync(pkts, p => this.Dist(p) < 25); } break; case ActivateEffects.PoisonGrenade: { BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.Throw, Color = new ARGB(0xffddff00), TargetId = Id, PosA = target }, p => this.Dist(p) < 25); Placeholder x = new Placeholder(Manager, 1500); x.Move(target.X, target.Y); Owner.EnterWorld(x); Owner.Timers.Add(new WorldTimer(1500, (world, t) => { Owner.BroadcastPacket(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, Color = new ARGB(0xffddff00), TargetId = x.Id, PosA = new Position() { X = eff.Radius } }, null); List <Enemy> enemies = new List <Enemy>(); Owner.AOE(target, eff.Radius, false, enemy => PoisonEnemy(enemy as Enemy, eff)); })); } break; case ActivateEffects.RemoveNegativeConditions: { this.AOE(eff.Range / 2, true, player => { ApplyConditionEffect(NegativeEffs); }); BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffffffff), PosA = new Position() { X = eff.Range / 2 } }, p => this.Dist(p) < 25); } break; case ActivateEffects.RemoveNegativeConditionsSelf: { ApplyConditionEffect(NegativeEffs); BroadcastSync(new ShowEffectPacket() { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffffffff), PosA = new Position() { X = 1 } }, p => this.Dist(p) < 25); } break; case ActivateEffects.IncrementStat: { int idx = -1; switch ((StatsType)eff.Stats) { case StatsType.MaximumHP: idx = 0; break; case StatsType.MaximumMP: idx = 1; break; case StatsType.Attack: idx = 2; break; case StatsType.Defense: idx = 3; break; case StatsType.Speed: idx = 4; break; case StatsType.Vitality: idx = 5; break; case StatsType.Wisdom: idx = 6; break; case StatsType.Dexterity: idx = 7; break; } Stats[idx] += eff.Amount; int limit = int.Parse(Manager.GameData.ObjectTypeToElement[ObjectType].Element(StatsManager.StatsIndexToName(idx)).Attribute("max").Value); if (Stats[idx] > limit) { Stats[idx] = limit; } UpdateCount++; } break; case ActivateEffects.Dye: { if (item.Texture1 != 0) { Texture1 = item.Texture1; } if (item.Texture2 != 0) { Texture2 = item.Texture2; } SaveToCharacter(); } break; case ActivateEffects.Create: { ushort objType; if (!Manager.GameData.IdToObjectType.TryGetValue(eff.Id, out objType) || !Manager.GameData.Portals.ContainsKey(objType)) { break; } Entity entity = Resolve(Manager, objType); World w = Manager.GetWorld(Owner.Id); int TimeoutTime = Manager.GameData.Portals[objType].TimeoutTime; string DungName = Manager.GameData.Portals[objType].DungeonName; ARGB c = new ARGB(0x00FF00); entity.Move(X, Y); w.EnterWorld(entity); w.BroadcastPacket(new NotificationPacket { Color = c, Text = DungName + " opened by " + Client.Account.Name, ObjectId = Client.Player.Id }, null); w.BroadcastPacket(new TextPacket { BubbleTime = 0, Stars = -1, Name = "", Text = DungName + " opened by " + Client.Account.Name }, null); w.Timers.Add(new WorldTimer(TimeoutTime * 1000, (world, t) => { try { w.LeaveWorld(entity); } catch (Exception ex) { log.ErrorFormat("Couldn't despawn portal.\n{0}", ex); } })); } break; } } }
private void AEVampireBlast(RealmTime time, Item item, Position target, ActivateEffect eff) { var pkts = new List <Packet> { new ShowEffect() { EffectType = EffectType.Trail, TargetObjectId = Id, Pos1 = target, Color = new ARGB(0xFFFF0000) }, new ShowEffect { EffectType = EffectType.Diffuse, Color = new ARGB(0xFFFF0000), TargetObjectId = Id, Pos1 = target, Pos2 = new Position { X = target.X + eff.Radius, Y = target.Y } } }; var totalDmg = 0; var enemies = new List <Enemy>(); Owner.AOE(target, eff.Radius, false, enemy => { enemies.Add(enemy as Enemy); totalDmg += (enemy as Enemy).Damage(this, time, eff.TotalDamage, false); }); var players = new List <Player>(); this.AOE(eff.Radius, true, player => { if (!player.HasConditionEffect(ConditionEffects.Sick)) { players.Add(player as Player); ActivateHealHp(player as Player, totalDmg, pkts); } }); if (enemies.Count > 0) { var rand = new Random(); for (var i = 0; i < 5; i++) { var a = enemies[rand.Next(0, enemies.Count)]; var b = players[rand.Next(0, players.Count)]; pkts.Add(new ShowEffect() { EffectType = EffectType.Flow, TargetObjectId = b.Id, Pos1 = new Position() { X = a.X, Y = a.Y }, Color = new ARGB(0xffffffff) }); } } BroadcastSync(pkts, p => this.DistSqr(p) < RadiusSqr); }
public int Damage(Player from, RealmTime time, int dmg, int pen, bool noDef, Projectile proj, bool deathmark = false, params ConditionEffect[] effs) { if (zeroHealth) { return(0); } if (HasConditionEffect(ConditionEffects.Invincible)) { return(0); } if (!HasConditionEffect(ConditionEffects.Paused) && !HasConditionEffect(ConditionEffects.Stasis)) { int def = Defense; int res = Resilience; if (noDef) { def = 0; Resilience = 0; } if (from.Specialization == "Blood" && from.AbilityActiveDurations[2] != 0) { float totalhealth = from.Stats[0]; float dmgPercentage = from.HP / totalhealth; dmg = dmg + (int)(dmg * dmgPercentage); } if (from.Specialization == "Marksmanship" && from.AbilityActiveDurations[2] != 0) { from.bowBlessing = from.bowBlessing + 5; float blessing = from.bowBlessing; float dmgmodifier = blessing / 100; dmg = (int)(dmg * dmgmodifier); } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.FireBall && burning) { dmg = dmg * 3; } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.PoisonDagger) { from.poisons.Add(new Poison(this, proj.abil)); } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.ToxicBolt) { if (Owner != null) { Owner.BroadcastPacket(new ShowEffectPacket { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffddff00), PosA = new Position { X = proj.abil.Radius } }, null); Owner.AOE(new Position { X = this.X, Y = this.Y }, proj.abil.Radius, false, enemy => { from.poisons.Add(new Poison(enemy as Enemy, proj.abil)); }); } } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.FireBlast) { from.burns.Add(new Burn(this, proj.abil)); } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.FlameVolley) { from.burns.Add(new Burn(this, proj.abil)); } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.BlastVolley) { Owner.BroadcastPacket(new ShowEffectPacket { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffff5500), PosA = new Position { X = proj.abil.Radius } }, null); Owner.AOE(new Position { X = this.X, Y = this.Y }, proj.abil.Radius, false, enemy => { (enemy as Enemy).Damage(from, time, proj.abil.Damage, pen, false, null); if (burning) { from.burns.Add(new Burn(enemy as Enemy, proj.abil)); } }); } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.SkillShot) { float elapsed = time.TotalElapsedMs - proj.BeginTime; float dmgmodifier = elapsed / 1500; dmg = (int)(dmg + (dmg * dmgmodifier * 5)); } if (proj != null && proj.abil != null && proj.abil.Ability == ActivateAbilities.DeathArrow) { proj.deathhitcount++; dmg = dmg * proj.deathhitcount; } int effDmg = Math.Min((int)StatsManager.GetEnemyDamage(this, dmg, pen, def, res), HP); if (HasConditionEffect(ConditionEffects.Invulnerable)) { effDmg = 0; } HP -= effDmg; if (from.DeathMarked != null) { if (deathmark == false) { foreach (var i in from.DeathMarked.Keys) { if (i == this || i.Owner == null) { continue; } i.Damage(from, time, dmg / 10, pen, false, null, true); } } } ApplyConditionEffect(effs); if (effDmg != 0) { Owner.BroadcastPacket(new DamagePacket { TargetId = Id, Effects = 0, Damage = (ushort)effDmg, Killed = HP <= 0, BulletId = 0, ObjectId = from != null ? from.Id : -1 }, null); } if (from != null) { counter.HitBy(from, time, proj, effDmg); } if (HP <= 0 && Owner != null) { Death(time); } UpdateCount++; return(effDmg); } return(0); }
public override void Tick(RealmTime time) { if (remDuration <= 0 || charges >= 5 || deathstarted) { deathstarted = true; r++; if (charges > 0) { if (r % 1 == 0) { pkts.Add(new ShowEffectPacket { EffectType = EffectType.AreaBlast, TargetId = Id, Color = new ARGB(0xffC2F0FF), PosA = new Position { X = radius } }); Owner.AOE(new Position { X = X, Y = Y }, radius, false, enemy => { enemies.Add(enemy as Enemy); pkts.Add(new ShowEffectPacket { EffectType = EffectType.Lightning, TargetId = Id, Color = new ARGB(0xffC2F0FF), PosA = new Position { X = enemy.X, Y = enemy.Y }, PosB = new Position { X = 350 } }); }); playerOwner.BroadcastSync(pkts, p => this.Dist(p) < 25); foreach (var i in enemies) { i.Damage(playerOwner, time, damage, penetration, false, null); } charges--; } } else { Owner.LeaveWorld(this); } } else { remDuration -= time.ElaspedMsDelta; } if (remDuration > duration - 1000) { this.ValidateAndMove( X + direction.X * speed * time.ElaspedMsDelta / 1000, Y + direction.Y * speed * time.ElaspedMsDelta / 1000 ); } UpdateCount++; }