/// <summary> /// /// </summary> /// <param name="spellCast"></param> /// <returns></returns> private bool Cast(SpellCast spellCast) { var spell = spellCast.Spell; if (spellCast.Target is Entity target) { // TODO: https://github.com/WorldOfMogwais/WoMNetCore/issues/22 var concentrateRoll = 10; Adventure.Enqueue(AdventureLog.Info(this, target, ActivityLog.Create(ActivityLog.ActivityType.Cast, ActivityLog.ActivityState.Init, concentrateRoll, spell))); if (concentrateRoll > 1 && concentrateRoll > spell.Level) { Adventure.Enqueue(AdventureLog.Info(this, target, ActivityLog.Create(ActivityLog.ActivityType.Cast, ActivityLog.ActivityState.Success, concentrateRoll, spell))); spell.SpellEffect(this, target); } else { Adventure.Enqueue(AdventureLog.Info(this, target, ActivityLog.Create(ActivityLog.ActivityType.Cast, ActivityLog.ActivityState.Fail, concentrateRoll, spell))); } Adventure.Enqueue(AdventureLog.Attacked(this, target)); return(true); } return(false); }
/// <summary> /// /// </summary> /// <param name="entity"></param> public void Loot(AdventureEntity entity) { // only allow mogwais to loot if (!(this is Mogwai.Mogwai mogwai)) { return; } if (entity.LootState == LootState.None || entity.LootState == LootState.Looted) { return; } var activity = ActivityLog.Create(ActivityLog.ActivityType.Loot, ActivityLog.ActivityState.None, new int[] { }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, entity, activity)); if (entity.Treasure != null) { activity = ActivityLog.Create(ActivityLog.ActivityType.Treasure, ActivityLog.ActivityState.Success, new int[] { }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, entity, activity)); mogwai.AddGold(entity.Treasure.Gold); } else { activity = ActivityLog.Create(ActivityLog.ActivityType.Treasure, ActivityLog.ActivityState.Fail, new int[] { }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, entity, activity)); } entity.LootState = LootState.Looted; }
/// <summary> /// /// </summary> /// <param name="damageAmount"></param> /// <param name="damageType"></param> public void Damage(int damageAmount, DamageType damageType) { // no damage return or same for dead entities if (damageAmount <= 0 || IsDead) { return; } var activity = ActivityLog.Create(ActivityLog.ActivityType.Damage, ActivityLog.ActivityState.None, new int[] { damageAmount, (int)damageType }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, null, activity)); CurrentHitPoints -= damageAmount; if (!CanAct) { activity = ActivityLog.Create(ActivityLog.ActivityType.HealthState, ActivityLog.ActivityState.None, new int[] { (int)HealthState }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, null, activity)); } if (IsDead) { activity = ActivityLog.Create(ActivityLog.ActivityType.HealthState, ActivityLog.ActivityState.None, new int[] { (int)HealthState }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, null, activity)); Map.DeadEntity(this); } }
/// <summary> /// /// </summary> /// <param name="weaponAttack"></param> /// <returns></returns> private void Attack(WeaponAttack weaponAttack) { var attackTimes = weaponAttack.ActionType == ActionType.Full ? BaseAttackBonus.Length : 1; var weapon = weaponAttack.Weapon; var target = weaponAttack.Target as Entity; //Console.WriteLine($"{Name}: is attacking {attackTimes} times"); // all attacks are calculated Parallel.For(0, attackTimes, (attackIndex, state) => { // break when target is null or dead, no more attacks on dead monsters. if (target == null || target.IsDead) { state.Break(); } var attackRolls = AttackRolls(attackIndex, weapon.CriticalMinRoll); var attack = AttackRoll(attackRolls, target.ArmorClass, out var criticalCounts); Adventure.Enqueue(AdventureLog.Info(this, target, ActivityLog.Create(ActivityLog.ActivityType.Attack, ActivityLog.ActivityState.Init, new int[] { attackIndex, attack, criticalCounts }, weaponAttack))); if (attack > target.ArmorClass || criticalCounts > 0) { var damage = DamageRoll(weapon, Dice); var criticalDamage = 0; if (criticalCounts > 0) { for (var i = 0; i < weapon.CriticalMultiplier - 1; i++) { criticalDamage += DamageRoll(weapon, Dice); } } Adventure.Enqueue(AdventureLog.Info(this, target, ActivityLog.Create(ActivityLog.ActivityType.Attack, ActivityLog.ActivityState.Success, new int[] { attackIndex, attack, criticalCounts, damage, criticalDamage, (int)DamageType.Weapon }, weaponAttack))); target.Damage(damage + criticalDamage, DamageType.Weapon); } else { Adventure.Enqueue(AdventureLog.Info(this, target, ActivityLog.Create(ActivityLog.ActivityType.Attack, ActivityLog.ActivityState.Fail, new int[] { attackIndex, attack, criticalCounts }, weaponAttack))); } Adventure.Enqueue(AdventureLog.Attacked(this, target)); }); }
/// <summary> /// Passive level up, includes for example hit point roles. /// </summary> private void LevelUp() { var activity = ActivityLog.Create(ActivityLog.ActivityType.Level, ActivityLog.ActivityState.None, new int[] { CurrentLevel }, null); History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, null, activity)); // level up grant free revive SpecialAction(SpecialType.Reviving); // level up grant free heal SpecialAction(SpecialType.Heal); }
/// <inheritdoc /> public override void AddGold(int gold) { var activity = ActivityLog.Create(ActivityLog.ActivityType.Gold, ActivityLog.ActivityState.None, new int[] { gold }, null); History.Add(LogType.Info, activity); if (Adventure != null) { Adventure.Enqueue(AdventureLog.Info(this, null, activity)); Adventure.AdventureStats[AdventureStats.Gold] = Adventure.AdventureStats[AdventureStats.Gold] + gold; } Wealth.Gold += gold; }
/// <inheritdoc /> public override void AddExp(double exp, Monster.Monster monster = null) { var activity = ActivityLog.Create(ActivityLog.ActivityType.Exp, ActivityLog.ActivityState.None, new int[] { (int)exp }, monster); History.Add(LogType.Info, activity); if (Adventure != null) { Adventure.Enqueue(AdventureLog.Info(this, null, activity)); Adventure.AdventureStats[AdventureStats.Experience] = Adventure.AdventureStats[AdventureStats.Experience] + exp; } Exp += exp; while (Exp >= XpToLevelUp) { CurrentLevel += 1; LevelShifts.Add(_currentShift.Height); LevelUp(); } }
/// <summary> /// /// </summary> /// <param name="healAmount"></param> /// <param name="healType"></param> public void Heal(int healAmount, HealType healType) { var missingHealth = MaxHitPoints - CurrentHitPoints; if (missingHealth <= 0 || healAmount <= 0) { return; } if (missingHealth < healAmount) { healAmount = missingHealth; } var activity = ActivityLog.Create(ActivityLog.ActivityType.Heal, ActivityLog.ActivityState.None, new int[] { healAmount, (int)healType }, null); Mogwai.Mogwai.History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, null, activity)); CurrentHitPoints += healAmount; }
/// <summary> /// /// </summary> /// <param name="classType"></param> private void LevelClass(ClassType classType) { if (!CanLevelClass(out _)) { Log.Warn("Not allowed class leveling action."); return; } var classes = Classes.FirstOrDefault(p => p.ClassType == classType); if (Classes.Count == 0 || classes == null) { Classes.Insert(0, Model.Classes.Classes.GetClasses(classType)); } else if (Classes.Remove(classes)) { Classes.Insert(0, classes); } var classesLevels = Classes.Sum(p => p.ClassLevel); // do the class level up Classes[0].ClassLevelUp(); var dice = Shifts[LevelShifts[classesLevels]].MogwaiDice; // level class now LevelClass(dice); // initial class level if (classesLevels == 0) { AddGold(dice.Roll(Classes[0].WealthDiceRollEvent)); } var activity = ActivityLog.Create(ActivityLog.ActivityType.LevelClass, ActivityLog.ActivityState.None, new int[] { (int)classType }, null); History.Add(LogType.Info, activity); Adventure?.Enqueue(AdventureLog.Info(this, null, activity)); }