public bool OnCast(Character caster, string args) { if (Map.IsNextToWall(caster)) { if (!Rules.BreakHideSpell(caster)) { bool giveXP = false; if (!caster.IsHidden && caster.BaseProfession == Character.ClassType.Thief) { giveXP = true; } Effect.CreateCharacterEffect(Effect.EffectTypes.Hide_in_Shadows, 1, caster, 0, caster); caster.WriteToDisplay("You fade into the shadows."); if (giveXP) { Skills.GiveSkillExp(caster, Skills.GetSkillLevel(caster.thievery) * 25, Globals.eSkillType.Thievery); } } else { return(false); } } else { caster.WriteToDisplay("You must be in the shadows to hide."); } return(true); }
public bool OnCommand(Character chr, string args) { if (chr.CommandWeight > 3) { return(true); } if (args == null || args == "") { if (!chr.CurrentCell.IsBalmFountain && !Map.IsNextToBalmFountain(chr)) { chr.WriteToDisplay("What do you want to drink?"); return(true); } else { goto balmFountain; } } if (chr.RightHand != null && chr.RightHand.itemType == Globals.eItemType.Potable) { if (chr.RightHand.baseType == Globals.eItemBaseType.Bottle) { Bottle.DrinkBottle((Bottle)chr.RightHand, chr); return(true); } } else if (chr.LeftHand != null && chr.LeftHand.itemType == Globals.eItemType.Potable) { if (chr.LeftHand.baseType == Globals.eItemBaseType.Bottle) { Bottle.DrinkBottle((Bottle)chr.LeftHand, chr); return(true); } } else //TODO: expand here to allow drinking from a fluid source (eg: fountains) { chr.WriteToDisplay("You are not holding a bottle."); return(true); } balmFountain: if (chr.CurrentCell.IsBalmFountain || Map.IsNextToBalmFountain(chr)) { chr.WriteToDisplay("You drink your fill of the refreshing fluid seeping from the balm tree."); int effectAmount = chr.HitsFull - chr.Hits; if (effectAmount < 0) { effectAmount = 0; } Effect.CreateCharacterEffect(Effect.EffectTypes.Balm, effectAmount, chr, -1, chr); } return(true); }
public bool OnCast(Character caster, string args) { args = args.Replace(" at ", ""); Character target = ReferenceSpell.FindAndConfirmSpellTarget(caster, args); int duration = 3; // 3 rounds, base if (caster.species == Globals.eSpecies.Arachnid || Autonomy.EntityBuilding.EntityLists.ARACHNID.Contains(caster.entity)) { duration += caster.Level / 2; } else if (caster.IsSpellWarmingProfession && caster.preppedSpell == GameSpell.GetSpell((int)GameSpell.GameSpellID.Create_Web)) { duration += Skills.GetSkillLevel(caster.magic) / 3; } duration += Rules.Dice.Next(-1, 1); if (target == null) { Cell targetCell = Map.GetCellRelevantToCell(caster.CurrentCell, args, false); if (targetCell != null) { AreaEffect effect = new AreaEffect(Effect.EffectTypes.Web, Cell.GRAPHIC_WEB, Skills.GetSkillLevel(caster.magic), duration, caster, targetCell); targetCell.EmitSound(ReferenceSpell.SoundFile); } } else { AreaEffect effect = new AreaEffect(Effect.EffectTypes.Web, Cell.GRAPHIC_WEB, Skills.GetSkillLevel(caster.magic), duration, caster, target.CurrentCell); if (target.CurrentCell != null) { target.CurrentCell.EmitSound(ReferenceSpell.SoundFile); } } if (target == null) { caster.WriteToDisplay("You cast " + ReferenceSpell.Name + "."); } else { caster.WriteToDisplay("You cast " + ReferenceSpell.Name + " at " + target.GetNameForActionResult(true).Replace("The ", "the ")); } return(true); }
public bool OnCast(Character caster, string args) { args = args.Replace(ReferenceSpell.Command, ""); args = args.Trim(); Character target = ReferenceSpell.FindAndConfirmSpellTarget(caster, args); Cell dCell = null; if (target == null) { dCell = Map.GetCellRelevantToCell(caster.CurrentCell, args, false); } else { dCell = target.CurrentCell; } if (dCell == null && target == null) { return(false); } //var tCell = Map.GetCellRelevantToCell(caster.CurrentCell, args, true); if (dCell != null) { // destroy all but attuned items foreach (var item in new List <Item>(dCell.Items)) { if (item.attunedID <= 0 && !item.IsArtifact() && !((item is Corpse) && (item as Corpse).IsPlayerCorpse)) { dCell.Remove(item); } } // do spell damage foreach (Character chr in dCell.Characters.Values) { if (Combat.DoSpellDamage(caster, chr, null, Skills.GetSkillLevel(caster.magic) * 10, ReferenceSpell.Name.ToLower()) == 1) { Rules.GiveAEKillExp(caster, chr); } } // destroy walls for a while if (!dCell.IsMagicDead) { if (dCell.DisplayGraphic == Cell.GRAPHIC_WALL) { var newDispGraphic = Rules.RollD(1, 20) >= 10 ? Cell.GRAPHIC_RUINS_LEFT : Cell.GRAPHIC_RUINS_RIGHT; var effect = new AreaEffect(Effect.EffectTypes.Illusion, newDispGraphic, 0, (int)Skills.GetSkillLevel(caster.magic) * 6, caster, dCell); dCell.SendShout("a wall crumbling."); } else if (dCell.DisplayGraphic == Cell.GRAPHIC_RUINS_LEFT || dCell.DisplayGraphic == Cell.GRAPHIC_RUINS_RIGHT) { var newDispGraphic = Rules.RollD(1, 20) >= 10 ? Cell.GRAPHIC_BARREN_LEFT : Cell.GRAPHIC_BARREN_RIGHT; var effect = new AreaEffect(Effect.EffectTypes.Illusion, newDispGraphic, 0, (int)Skills.GetSkillLevel(caster.magic) * 6, caster, dCell); dCell.SendShout("stone crumbling to dust."); } } } ReferenceSpell.SendGenericCastMessage(caster, null, true); return(true); }
public bool OnCommand(Character chr, string args) { if (chr.CommandWeight > 3) { return(true); } // args are null, send explanation of the dump command if (args == null) { chr.WriteToDisplay("Usage for the dump command:"); chr.WriteToDisplay("\"dump <item>\" - dump one <item> from sack onto ground"); chr.WriteToDisplay("\"dump <item> on <counter | altar>\" - dump one <item> from sack onto counter or altar"); chr.WriteToDisplay("\"dump <item> in locker\" - dump one <item> from sack into locker"); chr.WriteToDisplay("\"dump all <items>\" - dump all <items> from sack onto ground"); chr.WriteToDisplay("\"dump all <items> on <counter | altar>\" - dump all items from sack onto counter or altar"); chr.WriteToDisplay("\"dump all <items> in locker\" - dump all items from sack into locker"); return(true); } String[] sArgs = args.Split(" ".ToCharArray()); int upperBound = chr.sackList.Count; try { #region dump <item> if (sArgs.Length == 1) // "dump <item>" should just dump one item on the ground or send error message, then return { bool itemDumped = false; foreach (Item item in new System.Collections.Generic.List <Item>(chr.sackList)) { if (item.name == sArgs[0].Remove(sArgs[0].Length - 1, 1) || item.name == sArgs[0]) { chr.CurrentCell.Add(item); chr.sackList.Remove(item); if (item.itemType == Globals.eItemType.Coin) { if (item.coinValue > 1) { chr.WriteToDisplay("You dumped " + item.coinValue + " coins on the ground."); } else { chr.WriteToDisplay("You dumped " + item.coinValue + " coin on the ground."); } } else { chr.WriteToDisplay("You dumped " + item.shortDesc + " on the ground."); } itemDumped = true; break; // dump only one item then break out of here } } if (!itemDumped) { chr.WriteToDisplay("You do not have any " + sArgs[0] + " in your sack."); } return(true); } #endregion #region dump all <item> || dump all <item> <prep> <location> // "dump all <item>" or "dump all <item> <prep> <location>" if (sArgs.Length >= 2 && sArgs[0] == "all") { double counter = 0; // counter is used to determine how many, if any, items were dumped (for result message) // "dump all <item>" will dump all <item> on ground if (sArgs.Length == 2) { for (int x = upperBound - 1; x >= 0; x--) { Item item = (Item)chr.sackList[x]; // argument matches if (item.name == sArgs[1].Remove(sArgs[1].Length - 1, 1) || item.name == sArgs[1]) { chr.CurrentCell.Add(item); chr.sackList.RemoveAt(x); if (item.itemType == Globals.eItemType.Coin) { counter = item.coinValue; break; } else { counter++; } } } // send result message if (counter == 0) { chr.WriteToDisplay("You do not have any " + sArgs[1] + " in your sack."); } else { string plural = ""; if (counter > 1 && !sArgs[1].EndsWith("s")) { plural = "s"; } chr.WriteToDisplay("You dumped " + counter + " " + sArgs[1] + plural + " on the ground."); } return(true); } else { Item item = null; Item dumpedItem = null; switch (sArgs[2]) { case "on": // dump all <item> on counter/altar // if not standing near a counter or altar send error message and return if (!Map.IsNextToCounter(chr)) { chr.WriteToDisplay("You are not standing near a counter or altar."); return(true); } // iterate through sackList for (int x = upperBound - 1; x >= 0; x--) { item = (Item)chr.sackList[x]; if (item.name == sArgs[1].Remove(sArgs[1].Length - 1, 1) || item.name == sArgs[1]) { Map.PutItemOnCounter(chr, item); dumpedItem = item; chr.sackList.RemoveAt(x); counter++; } } if (dumpedItem != null && dumpedItem.itemType == Globals.eItemType.Coin) { if (dumpedItem.coinValue > 1) { chr.WriteToDisplay("You dumped " + dumpedItem.coinValue + " coins on the " + sArgs[3] + "."); } else { chr.WriteToDisplay("You dumped " + dumpedItem.coinValue + " coin on the " + sArgs[3] + "."); } } else { if (counter == 0) { chr.WriteToDisplay("You do not have any " + sArgs[1] + " in your sack."); } else if (counter == 1) { chr.WriteToDisplay("You dumped " + counter + " " + sArgs[1] + " on the " + sArgs[3] + "."); } else { string plural = ""; if (!sArgs[1].EndsWith("s")) { plural = "s"; } chr.WriteToDisplay("You dumped " + counter + " " + sArgs[1] + plural + " on the " + sArgs[3] + "."); } } break; case "in": // dump all <item> in locker -- currently (4/5/2013) lockers are the only thing you can dump items IN if (!chr.CurrentCell.IsLocker) { chr.WriteToDisplay("You are not standing next to your locker."); return(true); } else { for (int x = upperBound - 1; x >= 0; x--) { item = (Item)chr.sackList[x]; // argument match if (item.name == sArgs[1].Remove(sArgs[1].Length - 1, 1) || item.name == sArgs[1]) { if (item.itemType == Globals.eItemType.Coin) { chr.WriteToDisplay("You cannot store coins in your locker."); return(true); } if (chr.lockerList.Count < Character.MAX_LOCKER) { chr.lockerList.Add(item); chr.sackList.RemoveAt(x); counter++; } else { string plural = ""; if (!sArgs[1].EndsWith("s")) { plural = "s"; } chr.WriteToDisplay("You dumped " + counter + " " + sArgs[1] + plural + " into your locker. Your locker is full."); return(true); } } } chr.WriteToDisplay("You dumped " + counter + " " + sArgs[1] + "s into your locker."); } break; default: // by default, "dump all <item>" will dump all items to current cell for (int x = upperBound - 1; x >= 0; x--) { item = (Item)chr.sackList[x]; if (item.name == sArgs[0].Remove(sArgs[0].Length - 1, 1) || item.name == sArgs[0]) { chr.CurrentCell.Add(item); chr.sackList.RemoveAt(x); counter++; } } string plurals = ""; if (!sArgs[1].EndsWith("s")) { plurals = "s"; } chr.WriteToDisplay("You dumped " + counter + " " + sArgs[1] + plurals + " on the ground."); break; } } return(true); } #endregion #region dump <item> <prep> <location> switch (sArgs[1]) { case "on": for (int x = upperBound - 1; x >= 0; x--) { Item item = (Item)chr.sackList[x]; // argument match if (item.name == sArgs[0].Remove(sArgs[0].Length - 1, 1) || item.name == sArgs[0]) { if (Map.IsNextToCounter(chr)) { Map.PutItemOnCounter(chr, item); chr.sackList.RemoveAt(x); chr.WriteToDisplay("You dumped " + item.shortDesc + " on the " + sArgs[2] + "."); break; // stop at one item because first argument is not "all" } else { chr.CurrentCell.Add(item); chr.sackList.RemoveAt(x); chr.WriteToDisplay("You dumped " + item.shortDesc + " on the ground."); break; // stop at one item because first argument is not "all" } } } break; case "in": // dump <item> in locker -- currently (4/5/2013) lockers are the only thing you can dump items IN if (!chr.CurrentCell.IsLocker) { chr.WriteToDisplay("You are not standing next to your locker."); return(true); } else { if (chr.lockerList.Count >= Character.MAX_LOCKER) { chr.WriteToDisplay("Your locker is full."); return(true); } for (int x = upperBound - 1; x >= 0; x--) { Item item = (Item)chr.sackList[x]; // argument match if (item.name == sArgs[0].Remove(sArgs[0].Length - 1, 1) || item.name == sArgs[0]) { if (item.itemType == Globals.eItemType.Coin) { chr.WriteToDisplay("You cannot store coins in your locker."); break; } chr.lockerList.Add(item); chr.sackList.RemoveAt(x); chr.WriteToDisplay("You dumped " + item.shortDesc + " in your locker."); break; } } } break; default: // default is to dump item on the ground for (int x = upperBound - 1; x >= 0; x--) { Item item = (Item)chr.sackList[x]; if (item.name == sArgs[0].Remove(sArgs[0].Length - 1, 1) || item.name == sArgs[0]) { chr.CurrentCell.Add(item); chr.sackList.RemoveAt(x); chr.WriteToDisplay("You dumped " + item.shortDesc + " on the ground."); break; // stop at one item because argument 1 was not "all" } } break; } #endregion } catch (Exception e) { Utils.Log("Command.dump(" + args + ") by " + chr.GetLogString(), Utils.LogType.CommandFailure); Utils.LogException(e); } return(true); }
public bool OnCommand(Character chr, string args) { if (args == null) { chr.WriteToDisplay("Climb what?"); } else if (chr is NPC || (chr is PC && (chr as PC).ImpLevel > Globals.eImpLevel.USER) || chr.CommandWeight == 2) { chr.CommandType = CommandTasker.CommandType.Climb; string[] sArgs = args.Split(" ".ToCharArray()); if (sArgs[0].ToLower() == "up" || sArgs[0].ToLower() == "u") { if (chr.CurrentCell.IsOneHandClimbUp) { if (chr.RightHand == null || chr.LeftHand == null) { Map.MoveCharacter(chr, "climb up", ""); } else { chr.WriteToDisplay("You have slipped and fallen!"); } } else if (chr.CurrentCell.IsTwoHandClimbUp) { if (chr.RightHand == null && chr.LeftHand == null) { Map.MoveCharacter(chr, "climb up", ""); } else { chr.WriteToDisplay("You have slipped and fallen!"); } } else { chr.WriteToDisplay("There is nothing to climb here."); return(true); } } else if (sArgs[0].ToLower() == "down" || sArgs[0].ToLower() == "d") { if (chr.CurrentCell.IsOneHandClimbDown) { if (chr.RightHand == null || chr.LeftHand == null) { Map.MoveCharacter(chr, "climb down", ""); } else { chr.WriteToDisplay("You have slipped and fallen!"); } } else if (chr.CurrentCell.IsTwoHandClimbDown) { if (chr.RightHand == null && chr.LeftHand == null) { Map.MoveCharacter(chr, "climb down", ""); } else { chr.WriteToDisplay("Both hands must be empty to climb down here."); } } else { chr.WriteToDisplay("There is nothing to climb here."); } } else { chr.WriteToDisplay("You can't climb that!"); } } return(true); }
public bool OnPerform(Character chr, string args) { if (args == null) { chr.WriteToDisplay("Assasinate who?"); return(false); } string[] sArgs = args.Split(" ".ToCharArray()); Character target = TargetAcquisition.AcquireTarget(chr, args, GameWorld.Cell.DEFAULT_VISIBLE_DISTANCE, 0); // failed to find the target if (target == null) { chr.WriteToDisplay("You don't see a " + (sArgs.Length >= 2 ? sArgs[0] + " " + sArgs[1] : sArgs[0]) + " here."); return(false); } if (target.CurrentCell != chr.CurrentCell) { if (!PathTest.SuccessfulPathTest(PathTest.RESERVED_NAME_JUMPKICKCOMMAND, chr.CurrentCell, target.CurrentCell)) { return(false); } } if (target.IsPC) { chr.WriteToDisplay("Fellow players may not be assassinated, yet."); return(false); } if (target is NPC && (target as NPC).lairCritter) { chr.WriteToDisplay("Your target has a lair and is on guard for assassination attempts."); return(false); } if (target.seenList.Contains(chr) && (target is PC || ((target is NPC) && (target as NPC).enemyList.Contains(chr)))) { chr.WriteToDisplay("Your intended target is aware of your presence."); return(false); } if (target is NPC && (target as NPC).friendList.Count > 0) { if ((target as NPC).friendList.Count == 1 && (target as NPC).friendList.Contains(chr)) { // continue, thief was visible briefly and appeared as a friend } else { chr.WriteToDisplay("Your target has allies nearby. An assassination target must be alone."); return(false); } } if (target is NPC && (target as NPC).enemyList.Count > 0) { chr.WriteToDisplay("Your target has visible enemies nearby. An assassination target must be alone."); return(false); } // Only humans, humanoids and giantkin may be assassinated. if (!Autonomy.EntityBuilding.EntityLists.IsHumanOrHumanoid(target) && !Autonomy.EntityBuilding.EntityLists.IsGiantKin(target)) { chr.WriteToDisplay("Only humans, humanoids and giantkin may be the target of an assassination."); return(false); } // Unique entities cannot be assassinated. if (Autonomy.EntityBuilding.EntityLists.UNIQUE.Contains(target.entity)) { chr.WriteToDisplay("Unique entities cannot be assassinated. They have a level of perception that keeps them aware of such attempts."); return(false); } // Assassination requires Speed. if (!chr.HasSpeed) { chr.WriteToDisplay("You must be enchanted with Speed to carry out an assassination."); return(false); } int distance = DragonsSpine.GameWorld.Cell.GetCellDistance(chr.X, chr.Y, target.X, target.Y); int thieverySkillLevel = Skills.GetSkillLevel(chr.thievery); // check minimum thievery skill requirement for allowed distance if (distance > 2 && (thieverySkillLevel < MoveThreeAndAssassinateSkillRequirement)) { chr.WriteToDisplay("Your intended target is too far away. Improve your thievery skill."); return(false); } // verify path is not blocked if (distance > 0) { if (!PathTest.SuccessfulPathTest(PathTest.RESERVED_NAME_COMMANDSUFFIX, chr.CurrentCell, target.CurrentCell)) { chr.WriteToDisplay(GameSystems.Text.TextManager.PATH_IS_BLOCKED); return(false); } } Item weapon = null; if (chr.RightHand != null && chr.RightHand.itemType == Globals.eItemType.Weapon) { weapon = chr.RightHand; } else if (chr.LeftHand != null && chr.LeftHand.itemType == Globals.eItemType.Weapon) { weapon = chr.LeftHand; } if (weapon == null) { return(false); } chr.CommandType = CommandTasker.CommandType.Assassinate; chr.CurrentCell = target.CurrentCell; chr.updateMap = true; Combat.DoCombat(chr, target, weapon); chr.CommandsProcessed.RemoveAll(cmdType => cmdType == CommandTasker.CommandType.Assassinate); // give skill experience Skills.GiveSkillExp(chr, Skills.GetSkillLevel(chr.thievery) * 75, Globals.eSkillType.Thievery); if (!chr.HasSpeed || !Map.IsNextToWall(chr) || !Rules.FullStatCheck(chr, Globals.eAbilityStat.Dexterity)) { chr.IsHidden = false; } else if (thieverySkillLevel < RemainHiddenAfterAssassinate && !Rules.FullStatCheck(chr, Globals.eAbilityStat.Dexterity)) { Map.CheckHiddenStatus(chr); } if (chr.IsHidden && !chr.EffectsList[Effect.EffectTypes.Hide_in_Shadows].IsPermanent) { chr.WriteToDisplay(GameSystems.Text.TextManager.REMAINED_HIDDEN); } return(true); }
public bool OnPerform(Character chr, string args) { if (args == null) { chr.WriteToDisplay("Backstab who?"); return(false); } if (chr.RightHand == null && chr.LeftHand == null) { chr.WriteToDisplay("You are not holding a weapon to backstab with."); return(false); } if (Rules.GetEncumbrance(chr) > Globals.eEncumbranceLevel.Moderately) { chr.WriteToDisplay("You are too encumbered to backstab."); return(false); } Item weapon = null; if (chr.RightHand != null && chr.RightHand.itemType == Globals.eItemType.Weapon) { weapon = chr.RightHand; } else if (chr.LeftHand != null && chr.LeftHand.itemType == Globals.eItemType.Weapon) { weapon = chr.LeftHand; } if (weapon == null) { chr.WriteToDisplay("You are not holding a weapon you can backstab with."); return(false); } if (!AllowedBackstabItemBaseTypes.Contains(weapon.baseType)) { chr.WriteToDisplay("You are not holding a weapon you can backstab with."); return(false); } string[] sArgs = args.Split(" ".ToCharArray()); Character target = TargetAcquisition.AcquireTarget(chr, args, GameWorld.Cell.DEFAULT_VISIBLE_DISTANCE, 0); // failed to find the target if (target == null) { chr.WriteToDisplay("You don't see a " + (sArgs.Length >= 2 ? sArgs[0] + " " + sArgs[1] : sArgs[0]) + " here."); return(false); } if (target.seenList.Contains(chr)) { chr.WriteToDisplay("Your intended target is aware of your presence."); return(false); } if (!chr.HasSpeed) { chr.WriteToDisplay("You must be enchanted with Speed to perform a backstab."); return(false); } int distance = DragonsSpine.GameWorld.Cell.GetCellDistance(chr.X, chr.Y, target.X, target.Y); int thieverySkillLevel = Skills.GetSkillLevel(chr.thievery); // check minimum thievery skill requirement if (distance > 2 && (thieverySkillLevel < MoveThreeAndBackstabSkillRequirement)) { chr.WriteToDisplay("Your intended target is too far away. Improve your thievery skill."); return(false); } // verify path is not blocked if (distance > 0) { if (!PathTest.SuccessfulPathTest(PathTest.RESERVED_NAME_COMMANDSUFFIX, chr.CurrentCell, target.CurrentCell)) { chr.WriteToDisplay(GameSystems.Text.TextManager.PATH_IS_BLOCKED); return(false); } } chr.CommandType = CommandTasker.CommandType.Backstab; chr.CurrentCell = target.CurrentCell; chr.updateMap = true; Combat.DoCombat(chr, target, weapon); chr.CommandsProcessed.RemoveAll(cmdType => cmdType == CommandTasker.CommandType.Backstab); // give skill experience Skills.GiveSkillExp(chr, Skills.GetSkillLevel(chr.thievery) * 50, Globals.eSkillType.Thievery); if (thieverySkillLevel < RemainHiddenAfterBackstabWithSpeed && !Rules.FullStatCheck(chr, Globals.eAbilityStat.Dexterity)) { chr.IsHidden = false; } else if (!chr.HasSpeed || !Map.IsNextToWall(chr) || !Rules.FullStatCheck(chr, Globals.eAbilityStat.Dexterity)) { chr.IsHidden = false; } else { Map.CheckHiddenStatus(chr); } if (chr.IsHidden && !chr.EffectsList[Effect.EffectTypes.Hide_in_Shadows].IsPermanent) { chr.WriteToDisplay(GameSystems.Text.TextManager.REMAINED_HIDDEN); } return(true); }